mirror of
https://github.com/espressif/openthread.git
synced 2026-08-09 04:07:47 +00:00
[posix] radio only host side driver (#2690)
This commit is contained in:
@@ -47,6 +47,12 @@ after_success:
|
||||
|
||||
matrix:
|
||||
include:
|
||||
- env: BUILD_TARGET="posix-app-cli" VERBOSE=1
|
||||
os: linux
|
||||
compiler: gcc
|
||||
- env: BUILD_TARGET="posix-app-ncp" VERBOSE=1
|
||||
os: linux
|
||||
compiler: gcc
|
||||
- env: BUILD_TARGET="posix-distcheck" CC=clang-5.0 CXX=clang++-5.0 VERBOSE=1 VIRTUAL_TIME=1
|
||||
os: linux
|
||||
addons:
|
||||
|
||||
@@ -39,10 +39,10 @@ cd /tmp || die
|
||||
[ $TRAVIS_OS_NAME != linux ] || {
|
||||
sudo apt-get update || die
|
||||
|
||||
[ $BUILD_TARGET != posix-distcheck -a $BUILD_TARGET != posix-32-bit -a $BUILD_TARGET != posix-mtd -a $BUILD_TARGET != posix-ncp ] || {
|
||||
[ $BUILD_TARGET != posix-distcheck -a $BUILD_TARGET != posix-32-bit -a $BUILD_TARGET != posix-app-cli -a $BUILD_TARGET != posix-mtd -a $BUILD_TARGET != posix-ncp -a $BUILD_TARGET != posix-app-ncp ] || {
|
||||
pip install --user --upgrade pip || die
|
||||
pip install --user -r $TRAVIS_BUILD_DIR/tests/scripts/thread-cert/requirements.txt || die
|
||||
[ $BUILD_TARGET != posix-ncp ] || {
|
||||
[ $BUILD_TARGET != posix-ncp -a $BUILD_TARGET != posix-app-ncp ] || {
|
||||
# Packages used by ncp tools.
|
||||
pip install --user git+https://github.com/openthread/pyspinel || die
|
||||
}
|
||||
|
||||
@@ -432,6 +432,13 @@ set -x
|
||||
COVERAGE=1 CFLAGS=-m32 CXXFLAGS=-m32 LDFLAGS=-m32 make -f examples/Makefile-posix check || die
|
||||
}
|
||||
|
||||
[ $BUILD_TARGET != posix-app-cli ] || {
|
||||
./bootstrap || die
|
||||
make -f examples/Makefile-posix || die
|
||||
make -f src/posix/Makefile-posix || die
|
||||
OT_CLI_PATH="$(pwd)/$(ls output/posix/*/bin/ot-cli)" RADIO_DEVICE="$(pwd)/$(ls output/*/bin/ot-ncp-radio)" COVERAGE=1 make -f src/posix/Makefile-posix check || die
|
||||
}
|
||||
|
||||
[ $BUILD_TARGET != posix-mtd ] || {
|
||||
./bootstrap || die
|
||||
COVERAGE=1 CFLAGS=-m32 CXXFLAGS=-m32 LDFLAGS=-m32 USE_MTD=1 make -f examples/Makefile-posix check || die
|
||||
@@ -442,6 +449,13 @@ set -x
|
||||
make -f examples/Makefile-posix check configure_OPTIONS="--enable-ncp-app=ftd --with-ncp-bus=spi --with-examples=posix" || die
|
||||
}
|
||||
|
||||
[ $BUILD_TARGET != posix-app-ncp ] || {
|
||||
./bootstrap || die
|
||||
make -f examples/Makefile-posix || die
|
||||
make -f src/posix/Makefile-posix || die
|
||||
OT_NCP_PATH="$(pwd)/$(ls output/posix/*/bin/ot-ncp)" RADIO_DEVICE="$(pwd)/$(ls output/*/bin/ot-ncp-radio)" COVERAGE=1 NODE_TYPE=ncp-sim make -f src/posix/Makefile-posix check || die
|
||||
}
|
||||
|
||||
[ $BUILD_TARGET != posix-ncp ] || {
|
||||
./bootstrap || die
|
||||
NODE_TYPE=ncp-sim make -f examples/Makefile-posix check || die
|
||||
|
||||
+1
-1
@@ -50,8 +50,8 @@ AM_DISTCHECK_CONFIGURE_FLAGS = \
|
||||
|
||||
SUBDIRS = \
|
||||
include \
|
||||
src \
|
||||
third_party \
|
||||
src \
|
||||
examples \
|
||||
tests \
|
||||
tools \
|
||||
|
||||
+67
-6
@@ -373,6 +373,59 @@ NL_ENABLE_TESTS([yes])
|
||||
|
||||
AM_CONDITIONAL([OPENTHREAD_BUILD_TESTS], [test "${nl_cv_build_tests}" = "yes"])
|
||||
|
||||
#
|
||||
# Posix App
|
||||
#
|
||||
|
||||
AC_ARG_ENABLE(
|
||||
[posix-app],
|
||||
[AS_HELP_STRING([--enable-posix-app],[Enable POSIX app(no|ncp|cli|all) @<:@default=no@:>@.])],
|
||||
[
|
||||
case "${enableval}" in
|
||||
all|both|yes)
|
||||
enable_posix_app=yes
|
||||
OPENTHREAD_ENABLE_POSIX_APP=1
|
||||
OPENTHREAD_ENABLE_POSIX_APP_NCP=1
|
||||
OPENTHREAD_ENABLE_POSIX_APP_CLI=1
|
||||
;;
|
||||
no)
|
||||
enable_posix_app=no
|
||||
OPENTHREAD_ENABLE_POSIX_APP=0
|
||||
OPENTHREAD_ENABLE_POSIX_APP_NCP=0
|
||||
OPENTHREAD_ENABLE_POSIX_APP_CLI=0
|
||||
;;
|
||||
ncp)
|
||||
enable_posix_app=yes
|
||||
OPENTHREAD_ENABLE_POSIX_APP=1
|
||||
OPENTHREAD_ENABLE_POSIX_APP_NCP=1
|
||||
OPENTHREAD_ENABLE_POSIX_APP_CLI=0
|
||||
;;
|
||||
cli)
|
||||
enable_posix_app=yes
|
||||
OPENTHREAD_ENABLE_POSIX_APP=1
|
||||
OPENTHREAD_ENABLE_POSIX_APP_NCP=0
|
||||
OPENTHREAD_ENABLE_POSIX_APP_CLI=1
|
||||
;;
|
||||
*)
|
||||
AC_MSG_ERROR([Invalid value ${enableval} for --enable-posix-app])
|
||||
;;
|
||||
esac
|
||||
],
|
||||
[
|
||||
enable_posix_app=no
|
||||
OPENTHREAD_ENABLE_POSIX_APP=0
|
||||
OPENTHREAD_ENABLE_POSIX_APP_NCP=0
|
||||
OPENTHREAD_ENABLE_POSIX_APP_CLI=0])
|
||||
|
||||
AC_MSG_CHECKING([posix-app])
|
||||
AC_MSG_RESULT(${enable_posix_app})
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_POSIX_APP], [test "${OPENTHREAD_ENABLE_POSIX_APP}" == "1"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_POSIX_APP_NCP], [test "${OPENTHREAD_ENABLE_POSIX_APP_NCP}" == "1"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_POSIX_APP_CLI], [test "${OPENTHREAD_ENABLE_POSIX_APP_CLI}" == "1"])
|
||||
AC_SUBST(OPENTHREAD_ENABLE_POSIX_APP)
|
||||
AC_SUBST(OPENTHREAD_ENABLE_POSIX_APP_NCP)
|
||||
AC_SUBST(OPENTHREAD_ENABLE_POSIX_APP_CLI)
|
||||
|
||||
#
|
||||
# CLI Library
|
||||
#
|
||||
@@ -413,9 +466,9 @@ AC_ARG_ENABLE(cli-app,
|
||||
|
||||
AC_MSG_CHECKING([cli-app modes])
|
||||
AC_MSG_RESULT(${enable_cli_app})
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_CLI], [test "${enable_cli_app}" == "yes"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_CLI], [test "${enable_cli_app}" == "yes" -o "${OPENTHREAD_ENABLE_POSIX_APP_CLI}" == "1"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_CLI_MTD], [test "${enable_cli_app_mtd}" == "yes"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_CLI_FTD], [test "${enable_cli_app_ftd}" == "yes"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_CLI_FTD], [test "${enable_cli_app_ftd}" == "yes" -o "${OPENTHREAD_ENABLE_POSIX_APP_CLI}" == "1"])
|
||||
AC_SUBST(OPENTHREAD_ENABLE_CLI)
|
||||
AC_SUBST(OPENTHREAD_ENABLE_CLI_FTD)
|
||||
AC_SUBST(OPENTHREAD_ENABLE_CLI_MTD)
|
||||
@@ -496,9 +549,9 @@ AC_SUBST(OPENTHREAD_ENABLE_NCP_MTD)
|
||||
AC_SUBST(OPENTHREAD_ENABLE_NCP_FTD)
|
||||
AC_SUBST(OPENTHREAD_ENABLE_NCP_RADIO)
|
||||
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP], [test "${enable_ncp_app}" == "yes"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP], [test "${enable_ncp_app}" == "yes" -o "${OPENTHREAD_ENABLE_POSIX_APP_NCP}" == "1"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP_MTD], [test "${enable_ncp_app_mtd}" == "yes"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP_FTD], [test "${enable_ncp_app_ftd}" == "yes"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP_FTD], [test "${enable_ncp_app_ftd}" == "yes" -o "${OPENTHREAD_ENABLE_POSIX_APP_NCP}" == "1"])
|
||||
AM_CONDITIONAL([OPENTHREAD_ENABLE_NCP_RADIO], [test "${enable_ncp_app_radio}" == "yes"])
|
||||
|
||||
#
|
||||
@@ -1299,8 +1352,12 @@ AC_ARG_WITH(examples,
|
||||
[Specify the examples from one of: none, posix, cc2538, cc2650, cc2652, da15000, efr32, emsk, gp712, kw41z, nrf52840, samr21 @<:@default=none@:>@.])],
|
||||
[
|
||||
case "${with_examples}" in
|
||||
|
||||
none|posix|cc2538|cc2650|cc2652|da15000|efr32|emsk|gp712|kw41z|nrf52840|samr21)
|
||||
none)
|
||||
;;
|
||||
posix|cc2538|cc2650|cc2652|da15000|efr32|emsk|gp712|kw41z|nrf52840|samr21)
|
||||
if test ${enable_posix_app} = "yes"; then
|
||||
AC_MSG_ERROR([--with-examples must be none when POSIX apps are enabled by --enable-posix-app])
|
||||
fi
|
||||
;;
|
||||
*)
|
||||
AC_MSG_ERROR([Invalid value ${with_examples} for --with-examples])
|
||||
@@ -1446,6 +1503,8 @@ NL_ENABLE_DOCS([auto],[NO])
|
||||
|
||||
AM_CONDITIONAL(OPENTHREAD_BUILD_DOCS, [test "${nl_cv_build_docs}" = "yes"])
|
||||
|
||||
AM_CONDITIONAL(OPENTHREAD_POSIX, [test "${OPENTHREAD_ENABLE_POSIX_APP}" = "1" -o "${OPENTHREAD_EXAMPLES_POSIX}" = "1"])
|
||||
|
||||
#
|
||||
# Checks for libraries and packages.
|
||||
#
|
||||
@@ -1541,6 +1600,8 @@ src/cli/Makefile
|
||||
src/ncp/Makefile
|
||||
src/core/Makefile
|
||||
src/diag/Makefile
|
||||
src/posix/Makefile
|
||||
src/posix/platform/Makefile
|
||||
third_party/Makefile
|
||||
third_party/mbedtls/Makefile
|
||||
examples/Makefile
|
||||
|
||||
@@ -35,6 +35,7 @@ DIST_SUBDIRS = \
|
||||
cli \
|
||||
ncp \
|
||||
diag \
|
||||
posix \
|
||||
$(NULL)
|
||||
|
||||
# Always build (e.g. for 'make all') these subdirectories.
|
||||
@@ -55,12 +56,17 @@ if OPENTHREAD_ENABLE_DIAG
|
||||
SUBDIRS += diag
|
||||
endif
|
||||
|
||||
if OPENTHREAD_ENABLE_POSIX_APP
|
||||
SUBDIRS += posix
|
||||
endif
|
||||
|
||||
# Always pretty (e.g. for 'make pretty') these subdirectories.
|
||||
|
||||
PRETTY_SUBDIRS = \
|
||||
cli \
|
||||
core \
|
||||
ncp \
|
||||
posix \
|
||||
$(NULL)
|
||||
|
||||
include $(abs_top_nlbuild_autotools_dir)/automake/post.am
|
||||
|
||||
@@ -120,6 +120,11 @@ CPPFLAGS_COMMON = \
|
||||
$(OPENTHREAD_TARGET_DEFINES) \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_POSIX
|
||||
CPPFLAGS_COMMON += \
|
||||
-DOPENTHREAD_POSIX=1 \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
libopenthread_cli_mtd_a_CPPFLAGS = \
|
||||
-DOPENTHREAD_MTD=1 \
|
||||
|
||||
+5
-5
@@ -77,7 +77,7 @@
|
||||
#include "cli_coap.hpp"
|
||||
#endif
|
||||
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_EXAMPLES_POSIX
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_POSIX
|
||||
#include <openthread/platform/debug_uart.h>
|
||||
#endif
|
||||
|
||||
@@ -125,10 +125,10 @@ const struct Command Interpreter::sCommands[] = {
|
||||
{"eidcache", &Interpreter::ProcessEidCache},
|
||||
#endif
|
||||
{"eui64", &Interpreter::ProcessEui64},
|
||||
#ifdef OPENTHREAD_EXAMPLES_POSIX
|
||||
#if OPENTHREAD_POSIX
|
||||
{"exit", &Interpreter::ProcessExit},
|
||||
#endif
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_EXAMPLES_POSIX
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_POSIX
|
||||
{"logfilename", &Interpreter::ProcessLogFilename},
|
||||
#endif
|
||||
{"extaddr", &Interpreter::ProcessExtAddress},
|
||||
@@ -919,7 +919,7 @@ exit:
|
||||
AppendResult(error);
|
||||
}
|
||||
|
||||
#ifdef OPENTHREAD_EXAMPLES_POSIX
|
||||
#if OPENTHREAD_POSIX
|
||||
void Interpreter::ProcessExit(int argc, char *argv[])
|
||||
{
|
||||
exit(EXIT_SUCCESS);
|
||||
@@ -928,7 +928,7 @@ void Interpreter::ProcessExit(int argc, char *argv[])
|
||||
}
|
||||
#endif
|
||||
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_EXAMPLES_POSIX
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_POSIX
|
||||
|
||||
void Interpreter::ProcessLogFilename(int argc, char *argv[])
|
||||
{
|
||||
|
||||
+2
-2
@@ -215,10 +215,10 @@ private:
|
||||
void ProcessEidCache(int argc, char *argv[]);
|
||||
#endif
|
||||
void ProcessEui64(int argc, char *argv[]);
|
||||
#ifdef OPENTHREAD_EXAMPLES_POSIX
|
||||
#if OPENTHREAD_POSIX
|
||||
void ProcessExit(int argc, char *argv[]);
|
||||
#endif
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_EXAMPLES_POSIX
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART) && OPENTHREAD_POSIX
|
||||
void ProcessLogFilename(int argc, char *argv[]);
|
||||
#endif
|
||||
void ProcessExtAddress(int argc, char *argv[]);
|
||||
|
||||
@@ -132,7 +132,7 @@ void Uart::ReceiveTask(const uint8_t *aBuf, uint16_t aBufLength)
|
||||
|
||||
break;
|
||||
|
||||
#ifdef OPENTHREAD_EXAMPLES_POSIX
|
||||
#if OPENTHREAD_POSIX
|
||||
|
||||
case 0x04: // ASCII for Ctrl-D
|
||||
exit(EXIT_SUCCESS);
|
||||
|
||||
@@ -0,0 +1,294 @@
|
||||
#
|
||||
# Copyright (c) 2016, The OpenThread Authors.
|
||||
# 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.
|
||||
#
|
||||
|
||||
# Don't allow this top-level makefile's targets to be built in parallel.
|
||||
|
||||
.NOTPARALLEL:
|
||||
|
||||
COVERAGE ?= 0
|
||||
DEBUG ?= 0
|
||||
|
||||
ECHO := @echo
|
||||
MAKE := make
|
||||
MKDIR_P := mkdir -p
|
||||
LN_S := ln -s
|
||||
RM_F := rm -f
|
||||
|
||||
BuildJobs ?= 10
|
||||
|
||||
# If the user has asserted COVERAGE, alter the configuration options
|
||||
# accordingly.
|
||||
|
||||
configure_OPTIONS = \
|
||||
--enable-application-coap \
|
||||
--enable-border-router \
|
||||
--enable-cert-log \
|
||||
--enable-child-supervision \
|
||||
--enable-commissioner \
|
||||
--enable-dhcp6-client \
|
||||
--enable-dhcp6-server \
|
||||
--enable-diag \
|
||||
--enable-dns-client \
|
||||
--enable-jam-detection \
|
||||
--enable-joiner \
|
||||
--enable-legacy \
|
||||
--enable-mac-filter \
|
||||
--enable-posix-app=all \
|
||||
--enable-service \
|
||||
--enable-tmf-proxy \
|
||||
--with-ncp-bus=uart \
|
||||
$(NULL)
|
||||
|
||||
TopSourceDir := $(dir $(shell readlink $(firstword $(MAKEFILE_LIST))))../..
|
||||
AbsTopSourceDir := $(dir $(realpath $(firstword $(MAKEFILE_LIST))))../..
|
||||
|
||||
CONFIG_FILE = OPENTHREAD_PROJECT_CORE_CONFIG_FILE='\"openthread-core-posix-config.h\"'
|
||||
CONFIG_FILE_PATH = $(AbsTopSourceDir)/src/posix/platform
|
||||
|
||||
COMMONCFLAGS := \
|
||||
-O0 \
|
||||
-g \
|
||||
-D$(CONFIG_FILE) \
|
||||
-I$(CONFIG_FILE_PATH) \
|
||||
$(NULL)
|
||||
|
||||
CPPFLAGS += \
|
||||
$(COMMONCFLAGS) \
|
||||
$(NULL)
|
||||
|
||||
CFLAGS += \
|
||||
$(COMMONCFLAGS) \
|
||||
$(NULL)
|
||||
|
||||
CXXFLAGS += \
|
||||
$(COMMONCFLAGS) \
|
||||
$(NULL)
|
||||
|
||||
LDFLAGS += \
|
||||
$(COMMONCFLAGS) \
|
||||
$(NULL)
|
||||
|
||||
INSTALL := /usr/bin/install
|
||||
INSTALLFLAGS := -p
|
||||
|
||||
BuildPath = build/posix
|
||||
TopBuildDir = $(BuildPath)
|
||||
AbsTopBuildDir = $(PWD)/$(TopBuildDir)
|
||||
|
||||
ResultPath = output/posix
|
||||
TopResultDir = $(ResultPath)
|
||||
AbsTopResultDir = $(PWD)/$(TopResultDir)
|
||||
|
||||
TargetTuple = $(shell ${AbsTopSourceDir}/third_party/nlbuild-autotools/repo/third_party/autoconf/config.guess | sed -e 's/[[:digit:].]*$$//g')
|
||||
|
||||
ifndef BuildJobs
|
||||
BuildJobs := $(shell getconf _NPROCESSORS_ONLN)
|
||||
endif
|
||||
JOBSFLAG := -j$(BuildJobs)
|
||||
|
||||
#
|
||||
# configure-arch <target>
|
||||
#
|
||||
# Configure OpenThread for the specified target.
|
||||
#
|
||||
# target - The target to configure.
|
||||
#
|
||||
define configure-target
|
||||
$(ECHO) " CONFIG $(1)..."
|
||||
(cd $(BuildPath)/$(1) && $(AbsTopSourceDir)/configure \
|
||||
INSTALL="$(INSTALL) $(INSTALLFLAGS)" \
|
||||
CPPFLAGS="$(CPPFLAGS)" CFLAGS="$(CFLAGS)" CXXFLAGS="$(CXXFLAGS)" LDFLAGS="$(LDFLAGS)" \
|
||||
--prefix=/ \
|
||||
--exec-prefix=/$(1) \
|
||||
$(configure_OPTIONS))
|
||||
endef # configure-target
|
||||
|
||||
#
|
||||
# build-target <target>
|
||||
#
|
||||
# Build the OpenThread intermediate build products for the specified
|
||||
# target.
|
||||
#
|
||||
# target - The target to build.
|
||||
#
|
||||
define build-target
|
||||
$(ECHO) " BUILD $(1)"
|
||||
$(MAKE) $(JOBSFLAG) -C $(BuildPath)/$(1) --no-print-directory \
|
||||
all
|
||||
endef # build-target
|
||||
|
||||
#
|
||||
# check-target <target>
|
||||
#
|
||||
# Check (run unit tests) OpenThread for the specified target.
|
||||
#
|
||||
# target - The target to check.
|
||||
#
|
||||
define check-target
|
||||
$(ECHO) " CHECK $(1)"
|
||||
$(MAKE) $(JOBSFLAG) -C $(BuildPath)/$(1) --no-print-directory \
|
||||
check
|
||||
endef # check-target
|
||||
|
||||
#
|
||||
# distcheck-target <target>
|
||||
#
|
||||
# Check (run unit tests) OpenThread for the specified target.
|
||||
#
|
||||
# target - The target to distcheck.
|
||||
#
|
||||
define distcheck-target
|
||||
$(ECHO) " DISTCHECK $(1)"
|
||||
$(MAKE) $(JOBSFLAG) -C $(BuildPath)/$(1) --no-print-directory \
|
||||
distcheck
|
||||
endef # distcheck-target
|
||||
|
||||
#
|
||||
# coverage-target <target>
|
||||
#
|
||||
# Generate code coverage from unit tests for OpenThread for the
|
||||
# specified target.
|
||||
#
|
||||
# target - The target to generate code coverage for.
|
||||
#
|
||||
define coverage-target
|
||||
$(ECHO) " COVERAGE $(1)"
|
||||
$(MAKE) $(JOBSFLAG) -C $(BuildPath)/$(1) --no-print-directory \
|
||||
coverage
|
||||
endef # coverage-target
|
||||
|
||||
#
|
||||
# stage-target <target>
|
||||
#
|
||||
# Stage (install) the OpenThread final build products for the specified
|
||||
# target.
|
||||
#
|
||||
# target - The target to stage.
|
||||
#
|
||||
define stage-target
|
||||
$(ECHO) " STAGE $(1)"
|
||||
$(MAKE) $(JOBSFLAG) -C $(BuildPath)/$(1) --no-print-directory \
|
||||
DESTDIR=$(AbsTopResultDir) \
|
||||
install
|
||||
endef # stage-target
|
||||
|
||||
#
|
||||
# TARGET_template <target>
|
||||
#
|
||||
# Define macros, targets and rules to configure, build, and stage
|
||||
# OpenThread for a single target.
|
||||
#
|
||||
# target - The target to instantiate the template for.
|
||||
#
|
||||
define TARGET_template
|
||||
CONFIGURE_TARGETS += configure-$(1)
|
||||
BUILD_TARGETS += do-build-$(1)
|
||||
CHECK_TARGETS += check-$(1)
|
||||
DISTCHECK_TARGETS += distcheck-$(1)
|
||||
COVERAGE_TARGETS += coverage-$(1)
|
||||
STAGE_TARGETS += stage-$(1)
|
||||
BUILD_DIRS += $(BuildPath)/$(1)
|
||||
DIRECTORIES += $(BuildPath)/$(1)
|
||||
|
||||
configure-$(1): $(BuildPath)/$(1)/config.status
|
||||
|
||||
$(BuildPath)/$(1)/config.status: | $(BuildPath)/$(1)
|
||||
$$(call configure-target,$(1))
|
||||
|
||||
do-build-$(1): configure-$(1)
|
||||
|
||||
do-build-$(1):
|
||||
+$$(call build-target,$(1))
|
||||
|
||||
check-$(1): do-build-$(1)
|
||||
|
||||
check-$(1):
|
||||
+$$(call check-target,$(1))
|
||||
|
||||
distcheck-$(1): do-build-$(1)
|
||||
|
||||
distcheck-$(1):
|
||||
+$$(call distcheck-target,$(1))
|
||||
|
||||
coverage-$(1): do-build-$(1)
|
||||
|
||||
coverage-$(1):
|
||||
+$$(call coverage-target,$(1))
|
||||
|
||||
stage-$(1): do-build-$(1)
|
||||
|
||||
stage-$(1): | $(TopResultDir)
|
||||
$$(call stage-target,$(1))
|
||||
|
||||
$(1): stage-$(1)
|
||||
endef # TARGET_template
|
||||
|
||||
.DEFAULT_GOAL := all
|
||||
|
||||
all: stage
|
||||
|
||||
# Instantiate an target-specific build template for the target.
|
||||
|
||||
$(eval $(call TARGET_template,$(TargetTuple)))
|
||||
|
||||
#
|
||||
# Common / Finalization
|
||||
#
|
||||
|
||||
configure: $(CONFIGURE_TARGETS)
|
||||
|
||||
build: $(BUILD_TARGETS)
|
||||
|
||||
check: $(CHECK_TARGETS)
|
||||
|
||||
distcheck: $(DISTCHECK_TARGETS)
|
||||
|
||||
coverage: $(COVERAGE_TARGETS)
|
||||
|
||||
stage: $(STAGE_TARGETS)
|
||||
|
||||
DIRECTORIES = $(TopResultDir) $(TopResultDir)/$(TargetTuple)/lib $(BUILD_DIRS)
|
||||
|
||||
CLEAN_DIRS = $(TopResultDir) $(BUILD_DIRS)
|
||||
|
||||
all: stage
|
||||
|
||||
$(DIRECTORIES):
|
||||
$(ECHO) " MKDIR $@"
|
||||
@$(MKDIR_P) "$@"
|
||||
|
||||
clean:
|
||||
$(ECHO) " CLEAN"
|
||||
@$(RM_F) -r $(CLEAN_DIRS)
|
||||
|
||||
help:
|
||||
$(ECHO) "Simply type 'make -f $(firstword $(MAKEFILE_LIST))' to build OpenThread for the following "
|
||||
$(ECHO) "target:"
|
||||
$(ECHO) ""
|
||||
$(ECHO) " $(TargetTuple)"
|
||||
$(ECHO) ""
|
||||
@@ -0,0 +1,150 @@
|
||||
#
|
||||
# Copyright (c) 2018, The OpenThread Authors.
|
||||
# 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
|
||||
|
||||
# Always package (e.g. for 'make dist') these subdirectories.
|
||||
|
||||
DIST_SUBDIRS = \
|
||||
platform \
|
||||
$(NULL)
|
||||
|
||||
# Always build (e.g. for 'make all') these subdirectories.
|
||||
|
||||
SUBDIRS = \
|
||||
platform \
|
||||
$(NULL)
|
||||
|
||||
# Always pretty (e.g. for 'make pretty') these subdirectories.
|
||||
|
||||
PRETTY_SUBDIRS = \
|
||||
platform \
|
||||
$(NULL)
|
||||
|
||||
CPPFLAGS_COMMON = \
|
||||
-I$(top_srcdir)/include \
|
||||
-I$(top_srcdir)/src/core \
|
||||
-I$(top_srcdir)/src/posix/platform \
|
||||
-D_GNU_SOURCE \
|
||||
$(NULL)
|
||||
|
||||
LIBTOOLFLAGS_COMMON = --preserve-dup-deps
|
||||
|
||||
LDADD_COMMON = \
|
||||
$(top_builddir)/src/posix/platform/libopenthread-posix.a \
|
||||
-lstdc++ \
|
||||
-lutil \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_BUILTIN_MBEDTLS
|
||||
LDADD_COMMON += \
|
||||
$(top_builddir)/third_party/mbedtls/libmbedcrypto.a \
|
||||
$(NULL)
|
||||
endif # OPENTHREAD_ENABLE_BUILTIN_MBEDTLS
|
||||
|
||||
if OPENTHREAD_ENABLE_DIAG
|
||||
LDADD_COMMON += \
|
||||
$(top_builddir)/src/diag/libopenthread-diag.a \
|
||||
$(NULL)
|
||||
endif # OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
bin_PROGRAMS = \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_POSIX_APP_NCP
|
||||
bin_PROGRAMS += \
|
||||
ot-ncp \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
ot_ncp_CPPFLAGS = \
|
||||
$(CPPFLAGS_COMMON) \
|
||||
-DOPENTHREAD_POSIX_APP=1 \
|
||||
$(NULL)
|
||||
|
||||
ot_ncp_SOURCES = \
|
||||
main.c \
|
||||
$(NULL)
|
||||
|
||||
ot_ncp_LDADD = \
|
||||
$(top_builddir)/src/ncp/libopenthread-ncp-ftd.a \
|
||||
$(top_builddir)/src/core/libopenthread-ftd.a \
|
||||
$(LDADD_COMMON) \
|
||||
$(top_builddir)/src/core/libopenthread-ftd.a \
|
||||
$(LDADD_COMMON) \
|
||||
$(NULL)
|
||||
|
||||
ot_ncp_LDFLAGS = \
|
||||
$(LDFLAGS_COMMON) \
|
||||
$(NULL)
|
||||
|
||||
ot_ncp_LIBTOOLFLAGS = \
|
||||
$(LIBTOOLFLAGS_COMMON) \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_POSIX_APP_CLI
|
||||
bin_PROGRAMS += \
|
||||
ot-cli \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
ot_cli_CPPFLAGS = \
|
||||
$(CPPFLAGS_COMMON) \
|
||||
-DOPENTHREAD_POSIX_APP=2 \
|
||||
$(NULL)
|
||||
|
||||
ot_cli_SOURCES = \
|
||||
main.c \
|
||||
$(NULL)
|
||||
|
||||
ot_cli_LDADD = \
|
||||
$(top_builddir)/src/cli/libopenthread-cli-ftd.a \
|
||||
$(top_builddir)/src/core/libopenthread-ftd.a \
|
||||
$(LDADD_COMMON) \
|
||||
$(top_builddir)/src/core/libopenthread-ftd.a \
|
||||
$(LDADD_COMMON) \
|
||||
$(NULL)
|
||||
|
||||
ot_cli_LDFLAGS = \
|
||||
$(LDFLAGS_COMMON) \
|
||||
$(NULL)
|
||||
|
||||
ot_cli_LIBTOOLFLAGS = \
|
||||
$(LIBTOOLFLAGS_COMMON) \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_ENABLE_LINKER_MAP
|
||||
ot_ncp_LDFLAGS += -Wl,-Map=ot-cli-ftd.map
|
||||
ot_cli_LDFLAGS += -Wl,-Map=ot-cli-mtd.map
|
||||
endif
|
||||
|
||||
if OPENTHREAD_BUILD_COVERAGE
|
||||
CLEANFILES = $(wildcard *.gcda *.gcno)
|
||||
endif # OPENTHREAD_BUILD_COVERAGE
|
||||
|
||||
include $(abs_top_nlbuild_autotools_dir)/automake/post.am
|
||||
@@ -0,0 +1,108 @@
|
||||
/*
|
||||
* Copyright (c) 2018, The OpenThread Authors.
|
||||
* 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 <assert.h>
|
||||
|
||||
#include <openthread-core-config.h>
|
||||
#include <openthread/config.h>
|
||||
|
||||
#define OPENTHREAD_POSIX_APP_NCP 1
|
||||
#define OPENTHREAD_POSIX_APP_CLI 2
|
||||
|
||||
#include <openthread/diag.h>
|
||||
#if OPENTHREAD_POSIX_APP == OPENTHREAD_POSIX_APP_NCP
|
||||
#include <openthread/ncp.h>
|
||||
#elif OPENTHREAD_POSIX_APP == OPENTHREAD_POSIX_APP_CLI
|
||||
#include <openthread/cli.h>
|
||||
#else
|
||||
#error "Unknown posix app mode!"
|
||||
#endif
|
||||
#include <openthread/openthread.h>
|
||||
#include <openthread/platform/logging.h>
|
||||
|
||||
#include "platform.h"
|
||||
|
||||
void otTaskletsSignalPending(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
otInstance *sInstance;
|
||||
|
||||
pseudo_reset:
|
||||
|
||||
PlatformInit(argc, argv);
|
||||
|
||||
sInstance = otInstanceInitSingle();
|
||||
assert(sInstance);
|
||||
|
||||
#if OPENTHREAD_POSIX_APP == OPENTHREAD_POSIX_APP_NCP
|
||||
otNcpInit(sInstance);
|
||||
#elif OPENTHREAD_POSIX_APP == OPENTHREAD_POSIX_APP_CLI
|
||||
otCliUartInit(sInstance);
|
||||
#endif
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
otDiagInit(sInstance);
|
||||
#endif
|
||||
|
||||
while (!PlatformPseudoResetWasRequested())
|
||||
{
|
||||
otTaskletsProcess(sInstance);
|
||||
PlatformProcessDrivers(sInstance);
|
||||
}
|
||||
|
||||
otInstanceFinalize(sInstance);
|
||||
|
||||
goto pseudo_reset;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Provide, if required an "otPlatLog()" function
|
||||
*/
|
||||
#if OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_APP
|
||||
void otPlatLog(otLogLevel aLogLevel, otLogRegion aLogRegion, const char *aFormat, ...)
|
||||
{
|
||||
OT_UNUSED_VARIABLE(aLogLevel);
|
||||
OT_UNUSED_VARIABLE(aLogRegion);
|
||||
OT_UNUSED_VARIABLE(aFormat);
|
||||
|
||||
va_list ap;
|
||||
va_start(ap, aFormat);
|
||||
#if OPENTHREAD_POSIX_APP == OPENTHREAD_POSIX_APP_NCP
|
||||
otCliPlatLogv(aLogLevel, aLogRegion, aFormat, ap);
|
||||
#elif OPENTHREAD_POSIX_APP == OPENTHREAD_POSIX_APP_CLI
|
||||
otNcpPlatLogv(aLogLevel, aLogRegion, aFormat, ap);
|
||||
#endif
|
||||
va_end(ap);
|
||||
}
|
||||
#endif
|
||||
@@ -0,0 +1,75 @@
|
||||
#
|
||||
# Copyright (c) 2016-2018, The OpenThread Authors.
|
||||
# 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-posix.a
|
||||
|
||||
libopenthread_posix_a_CPPFLAGS = \
|
||||
-I$(top_srcdir)/include \
|
||||
-I$(top_srcdir)/src/core \
|
||||
-I$(top_srcdir)/src/ncp \
|
||||
-I$(top_srcdir)/src/posix/platform \
|
||||
-D_GNU_SOURCE \
|
||||
$(NULL)
|
||||
|
||||
libopenthread_posix_a_SOURCES = \
|
||||
alarm.c \
|
||||
diag.c \
|
||||
flash.c \
|
||||
frame_queue.cpp \
|
||||
hdlc.cpp \
|
||||
logging.c \
|
||||
misc.c \
|
||||
platform.c \
|
||||
radio_spinel.cpp \
|
||||
random.c \
|
||||
settings.cpp \
|
||||
spi-stubs.c \
|
||||
spinel.c \
|
||||
uart.c \
|
||||
$(NULL)
|
||||
|
||||
noinst_HEADERS = \
|
||||
flash.h \
|
||||
frame_queue.hpp \
|
||||
platform.h \
|
||||
platform-posix.h \
|
||||
radio_spinel.hpp \
|
||||
$(NULL)
|
||||
|
||||
PRETTY_FILES = \
|
||||
$(libopenthread_posix_a_SOURCES) \
|
||||
$(noinst_HEADERS) \
|
||||
$(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,59 @@
|
||||
# OpenThread on POSIX
|
||||
|
||||
This directory contains platform drivers for POSIX with an external radio tranceiver.
|
||||
|
||||
## Build
|
||||
|
||||
```bash
|
||||
$ cd <path-to-openthread>
|
||||
$ ./bootstrap
|
||||
$ make -f src/posix/Makefile-posix
|
||||
```
|
||||
|
||||
After a successful build, the `elf` files are found in
|
||||
`<path-to-openthread>/output/posix/<platform>/bin`.
|
||||
|
||||
##
|
||||
|
||||
## Interact
|
||||
|
||||
1. Spawn the process:
|
||||
|
||||
`stty` is required.
|
||||
|
||||
```bash
|
||||
$ cd <path-to-openthread>/output/<platform>/bin
|
||||
$ ./ot-cli /dev/ttyUSB0 115200
|
||||
```
|
||||
|
||||
2. Type `help` for list of commands.
|
||||
|
||||
```bash
|
||||
> help
|
||||
help
|
||||
channel
|
||||
childtimeout
|
||||
contextreusedelay
|
||||
extaddr
|
||||
extpanid
|
||||
ipaddr
|
||||
keysequence
|
||||
leaderweight
|
||||
masterkey
|
||||
mode
|
||||
netdataregister
|
||||
networkidtimeout
|
||||
networkname
|
||||
panid
|
||||
ping
|
||||
prefix
|
||||
releaserouterid
|
||||
rloc16
|
||||
route
|
||||
routerupgradethreshold
|
||||
scan
|
||||
start
|
||||
state
|
||||
stop
|
||||
whitelist
|
||||
```
|
||||
@@ -0,0 +1,195 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 "platform-posix.h"
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <openthread/platform/alarm-micro.h>
|
||||
#include <openthread/platform/alarm-milli.h>
|
||||
#include <openthread/platform/diag.h>
|
||||
|
||||
#define MS_PER_S 1000
|
||||
#define US_PER_MS 1000
|
||||
#define US_PER_S 1000000
|
||||
|
||||
#define DEFAULT_TIMEOUT 10 // seconds
|
||||
|
||||
static bool sIsMsRunning = false;
|
||||
static uint32_t sMsAlarm = 0;
|
||||
|
||||
static bool sIsUsRunning = false;
|
||||
static uint32_t sUsAlarm = 0;
|
||||
|
||||
static uint32_t sSpeedUpFactor = 1;
|
||||
|
||||
static struct timeval sStart;
|
||||
|
||||
void platformAlarmInit(uint32_t aSpeedUpFactor)
|
||||
{
|
||||
sSpeedUpFactor = aSpeedUpFactor;
|
||||
gettimeofday(&sStart, NULL);
|
||||
}
|
||||
|
||||
uint32_t otPlatAlarmMilliGetNow(void)
|
||||
{
|
||||
struct timeval tv;
|
||||
|
||||
gettimeofday(&tv, NULL);
|
||||
timersub(&tv, &sStart, &tv);
|
||||
|
||||
return (uint32_t)(((uint64_t)tv.tv_sec * sSpeedUpFactor * MS_PER_S) +
|
||||
((uint64_t)tv.tv_usec * sSpeedUpFactor / US_PER_MS));
|
||||
}
|
||||
|
||||
void otPlatAlarmMilliStartAt(otInstance *aInstance, uint32_t aT0, uint32_t aDt)
|
||||
{
|
||||
(void)aInstance;
|
||||
sMsAlarm = aT0 + aDt;
|
||||
sIsMsRunning = true;
|
||||
}
|
||||
|
||||
void otPlatAlarmMilliStop(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
sIsMsRunning = false;
|
||||
}
|
||||
|
||||
uint32_t otPlatAlarmMicroGetNow(void)
|
||||
{
|
||||
struct timeval tv;
|
||||
|
||||
gettimeofday(&tv, NULL);
|
||||
timersub(&tv, &sStart, &tv);
|
||||
|
||||
return (uint32_t)(tv.tv_sec * US_PER_S + tv.tv_usec) * sSpeedUpFactor;
|
||||
}
|
||||
|
||||
void otPlatAlarmMicroStartAt(otInstance *aInstance, uint32_t aT0, uint32_t aDt)
|
||||
{
|
||||
(void)aInstance;
|
||||
sUsAlarm = aT0 + aDt;
|
||||
sIsUsRunning = true;
|
||||
}
|
||||
|
||||
void otPlatAlarmMicroStop(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
sIsUsRunning = false;
|
||||
}
|
||||
|
||||
void platformAlarmUpdateTimeout(struct timeval *aTimeout)
|
||||
{
|
||||
int32_t usRemaining = DEFAULT_TIMEOUT * US_PER_S;
|
||||
int32_t msRemaining = DEFAULT_TIMEOUT * MS_PER_S;
|
||||
|
||||
if (aTimeout == NULL)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (sIsUsRunning)
|
||||
{
|
||||
usRemaining = (int32_t)(sUsAlarm - otPlatAlarmMicroGetNow());
|
||||
}
|
||||
|
||||
if (sIsMsRunning)
|
||||
{
|
||||
msRemaining = (int32_t)(sMsAlarm - otPlatAlarmMilliGetNow());
|
||||
}
|
||||
|
||||
if (usRemaining <= 0 || msRemaining <= 0)
|
||||
{
|
||||
aTimeout->tv_sec = 0;
|
||||
aTimeout->tv_usec = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
int64_t remaining = ((int64_t)msRemaining) * US_PER_MS;
|
||||
|
||||
if (usRemaining < remaining)
|
||||
{
|
||||
remaining = usRemaining;
|
||||
}
|
||||
|
||||
remaining /= sSpeedUpFactor;
|
||||
|
||||
if (remaining == 0)
|
||||
{
|
||||
remaining = 1;
|
||||
}
|
||||
|
||||
aTimeout->tv_sec = (time_t)remaining / US_PER_S;
|
||||
aTimeout->tv_usec = remaining % US_PER_S;
|
||||
}
|
||||
}
|
||||
|
||||
void platformAlarmProcess(otInstance *aInstance)
|
||||
{
|
||||
int32_t remaining;
|
||||
|
||||
if (sIsMsRunning)
|
||||
{
|
||||
remaining = (int32_t)(sMsAlarm - otPlatAlarmMilliGetNow());
|
||||
|
||||
if (remaining <= 0)
|
||||
{
|
||||
sIsMsRunning = false;
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
if (otPlatDiagModeGet())
|
||||
{
|
||||
otPlatDiagAlarmFired(aInstance);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
otPlatAlarmMilliFired(aInstance);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#if OPENTHREAD_CONFIG_ENABLE_PLATFORM_USEC_TIMER
|
||||
|
||||
if (sIsUsRunning)
|
||||
{
|
||||
remaining = (int32_t)(sUsAlarm - otPlatAlarmMicroGetNow());
|
||||
|
||||
if (remaining <= 0)
|
||||
{
|
||||
sIsUsRunning = false;
|
||||
|
||||
otPlatAlarmMicroFired(aInstance);
|
||||
}
|
||||
}
|
||||
|
||||
#endif // OPENTHREAD_CONFIG_ENABLE_PLATFORM_USEC_TIMER
|
||||
}
|
||||
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
* Copyright (c) 2017, The OpenThread Authors.
|
||||
* 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 includes macros for validating runtime conditions.
|
||||
*/
|
||||
|
||||
#ifndef CODE_UTILS_H
|
||||
#define CODE_UTILS_H
|
||||
|
||||
/**
|
||||
* This checks for the specified condition, which is expected to
|
||||
* commonly be true, and branches to the local label 'exit' if the
|
||||
* condition is false.
|
||||
*
|
||||
* @param[in] aCondition A Boolean expression to be evaluated.
|
||||
*
|
||||
*/
|
||||
#define otEXPECT(aCondition) \
|
||||
do \
|
||||
{ \
|
||||
if (!(aCondition)) \
|
||||
{ \
|
||||
goto exit; \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
/**
|
||||
* This checks for the specified condition, which is expected to
|
||||
* commonly be true, and both executes @p anAction and branches to
|
||||
* the local label 'exit' if the condition is false.
|
||||
*
|
||||
* @param[in] aCondition A Boolean expression to be evaluated.
|
||||
* @param[in] aAction An expression or block to execute when the
|
||||
* assertion fails.
|
||||
*
|
||||
*/
|
||||
#define otEXPECT_ACTION(aCondition, aAction) \
|
||||
do \
|
||||
{ \
|
||||
if (!(aCondition)) \
|
||||
{ \
|
||||
aAction; \
|
||||
goto exit; \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
/**
|
||||
* This unconditionally executes @aAction and branches to the local
|
||||
* label 'exit'.
|
||||
*
|
||||
* @note The use of this interface implies neither success nor
|
||||
* failure for the overall exit status of the enclosing
|
||||
* function body.
|
||||
*
|
||||
* @param[in] aAction An expression or block to execute.
|
||||
*
|
||||
*/
|
||||
#define otEXIT_NOW(aAction) \
|
||||
do \
|
||||
{ \
|
||||
aAction; \
|
||||
goto exit; \
|
||||
} while (0)
|
||||
|
||||
#endif // CODE_UTILS_H
|
||||
@@ -0,0 +1,149 @@
|
||||
/*
|
||||
* Copyright (c) 2017, The OpenThread Authors.
|
||||
* 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 <openthread-core-config.h>
|
||||
#include <stdarg.h>
|
||||
#include <stdio.h>
|
||||
#include <openthread/config.h>
|
||||
|
||||
#include <openthread/types.h>
|
||||
#include <openthread/platform/alarm-milli.h>
|
||||
#include <openthread/platform/debug_uart.h>
|
||||
#include <openthread/platform/toolchain.h>
|
||||
|
||||
/*
|
||||
* Implementation note:
|
||||
* These are all "weak" so that a platform may if it chooses override the instance.
|
||||
*/
|
||||
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_printf(const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
va_start(ap, fmt);
|
||||
otPlatDebugUart_vprintf(fmt, ap);
|
||||
va_end(ap);
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_vprintf(const char *fmt, va_list ap)
|
||||
{
|
||||
char buf[128];
|
||||
/* by standard ...
|
||||
* vsnprintf() always null terminates
|
||||
*/
|
||||
vsnprintf(buf, sizeof(buf), fmt, ap);
|
||||
/* however ... some platforms have bugs */
|
||||
buf[sizeof(buf) - 1] = 0;
|
||||
otPlatDebugUart_puts_no_nl(buf);
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_write_bytes(const uint8_t *pBytes, int nBytes)
|
||||
{
|
||||
while (nBytes > 0)
|
||||
{
|
||||
otPlatDebugUart_putchar((int)(*pBytes));
|
||||
pBytes++;
|
||||
nBytes--;
|
||||
}
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_puts_no_nl(const char *s)
|
||||
{
|
||||
while (*s)
|
||||
{
|
||||
otPlatDebugUart_putchar(*s);
|
||||
s++;
|
||||
}
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_puts(const char *s)
|
||||
{
|
||||
otPlatDebugUart_puts_no_nl(s);
|
||||
otPlatDebugUart_putchar('\n');
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_putchar(int c)
|
||||
{
|
||||
/* map lf to crlf as needed */
|
||||
if (c == '\n')
|
||||
{
|
||||
otPlatDebugUart_putchar_raw('\r');
|
||||
}
|
||||
|
||||
otPlatDebugUart_putchar_raw(c);
|
||||
}
|
||||
|
||||
/* provide WEAK stubs for platforms that do not implement all functions */
|
||||
OT_TOOL_WEAK
|
||||
void otPlatDebugUart_putchar_raw(int c)
|
||||
{
|
||||
OT_UNUSED_VARIABLE(c);
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
int otPlatDebugUart_kbhit(void)
|
||||
{
|
||||
return 0; /* nothing */
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
int otPlatDebugUart_getc(void)
|
||||
{
|
||||
return -1; /* nothing */
|
||||
}
|
||||
|
||||
OT_TOOL_WEAK
|
||||
otError otPlatDebugUart_logfile(const char *filename)
|
||||
{
|
||||
OT_UNUSED_VARIABLE(filename);
|
||||
return OT_ERROR_FAILED;
|
||||
}
|
||||
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART)
|
||||
/* this should not be a WEAK function */
|
||||
void otPlatLog(otLogLevel aLogLevel, otLogRegion aLogRegion, const char *aFormat, ...)
|
||||
{
|
||||
va_list ap;
|
||||
uint32_t now;
|
||||
|
||||
OT_UNUSED_VARIABLE(aLogLevel);
|
||||
OT_UNUSED_VARIABLE(aLogRegion);
|
||||
|
||||
now = otPlatAlarmMilliGetNow();
|
||||
otPlatDebugUart_printf("%3d.%03d | ", (int)(now / 1000), (int)(now % 1000));
|
||||
va_start(ap, aFormat);
|
||||
otPlatDebugUart_vprintf(aFormat, ap);
|
||||
va_end(ap);
|
||||
|
||||
otPlatDebugUart_putchar('\n');
|
||||
}
|
||||
#endif
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 "platform-posix.h"
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <openthread/config.h>
|
||||
#include <openthread/openthread.h>
|
||||
#include <openthread/platform/alarm-milli.h>
|
||||
#include <openthread/platform/radio.h>
|
||||
|
||||
#if OPENTHREAD_ENABLE_DIAG
|
||||
|
||||
/**
|
||||
* Diagnostics mode variables.
|
||||
*
|
||||
*/
|
||||
static bool sDiagMode = false;
|
||||
|
||||
void otPlatDiagProcess(otInstance *aInstance, int argc, char *argv[], char *aOutput, size_t aOutputMaxLen)
|
||||
{
|
||||
// Add more plarform specific diagnostics features here.
|
||||
snprintf(aOutput, aOutputMaxLen, "diag feature '%s' is not supported\r\n", argv[0]);
|
||||
(void)argc;
|
||||
(void)aInstance;
|
||||
}
|
||||
|
||||
void otPlatDiagModeSet(bool aMode)
|
||||
{
|
||||
sDiagMode = aMode;
|
||||
}
|
||||
|
||||
bool otPlatDiagModeGet()
|
||||
{
|
||||
return sDiagMode;
|
||||
}
|
||||
|
||||
void otPlatDiagChannelSet(uint8_t aChannel)
|
||||
{
|
||||
(void)aChannel;
|
||||
}
|
||||
|
||||
void otPlatDiagTxPowerSet(int8_t aTxPower)
|
||||
{
|
||||
(void)aTxPower;
|
||||
}
|
||||
|
||||
void otPlatDiagRadioReceived(otInstance *aInstance, otRadioFrame *aFrame, otError aError)
|
||||
{
|
||||
(void)aInstance;
|
||||
(void)aFrame;
|
||||
(void)aError;
|
||||
}
|
||||
|
||||
void otPlatDiagAlarmCallback(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
}
|
||||
|
||||
#endif // OPENTHREAD_ENABLE_DIAG
|
||||
@@ -0,0 +1,163 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 "platform-posix.h"
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <inttypes.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <openthread/config.h>
|
||||
|
||||
#include "code_utils.h"
|
||||
#include "flash.h"
|
||||
|
||||
static int sFlashFd = -1;
|
||||
uint32_t sEraseAddress;
|
||||
|
||||
enum
|
||||
{
|
||||
FLASH_SIZE = 0x40000,
|
||||
FLASH_PAGE_SIZE = 0x800,
|
||||
FLASH_PAGE_NUM = 128,
|
||||
};
|
||||
|
||||
otError utilsFlashInit(void)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
char fileName[32];
|
||||
struct stat st;
|
||||
bool create = false;
|
||||
const char *offset = getenv("PORT_OFFSET");
|
||||
|
||||
memset(&st, 0, sizeof(st));
|
||||
|
||||
if (stat("tmp", &st) == -1)
|
||||
{
|
||||
mkdir("tmp", 0777);
|
||||
}
|
||||
|
||||
if (offset == NULL)
|
||||
{
|
||||
offset = "0";
|
||||
}
|
||||
|
||||
snprintf(fileName, sizeof(fileName), "tmp/%s_%" PRIx64 ".flash", offset, NODE_ID);
|
||||
|
||||
if (access(fileName, 0))
|
||||
{
|
||||
create = true;
|
||||
}
|
||||
|
||||
sFlashFd = open(fileName, O_RDWR | O_CREAT, 0666);
|
||||
lseek(sFlashFd, 0, SEEK_SET);
|
||||
|
||||
otEXPECT_ACTION(sFlashFd >= 0, error = OT_ERROR_FAILED);
|
||||
|
||||
if (create)
|
||||
{
|
||||
for (uint16_t index = 0; index < FLASH_PAGE_NUM; index++)
|
||||
{
|
||||
error = utilsFlashErasePage(index * FLASH_PAGE_SIZE);
|
||||
otEXPECT(error == OT_ERROR_NONE);
|
||||
}
|
||||
}
|
||||
|
||||
exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
uint32_t utilsFlashGetSize(void)
|
||||
{
|
||||
return FLASH_SIZE;
|
||||
}
|
||||
|
||||
otError utilsFlashErasePage(uint32_t aAddress)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
uint32_t address;
|
||||
uint8_t dummyPage[FLASH_SIZE];
|
||||
|
||||
otEXPECT_ACTION(sFlashFd >= 0, error = OT_ERROR_FAILED);
|
||||
otEXPECT_ACTION(aAddress < FLASH_SIZE, error = OT_ERROR_INVALID_ARGS);
|
||||
|
||||
// Get start address of the flash page that includes aAddress
|
||||
address = aAddress & (~(uint32_t)(FLASH_PAGE_SIZE - 1));
|
||||
|
||||
// set the page to the erased state.
|
||||
memset((void *)(&dummyPage[0]), 0xff, FLASH_PAGE_SIZE);
|
||||
|
||||
// Write the page
|
||||
ssize_t r;
|
||||
r = pwrite(sFlashFd, &(dummyPage[0]), FLASH_PAGE_SIZE, (off_t)address);
|
||||
otEXPECT_ACTION(((int)r) == ((int)(FLASH_PAGE_SIZE)), error = OT_ERROR_FAILED);
|
||||
|
||||
exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
otError utilsFlashStatusWait(uint32_t aTimeout)
|
||||
{
|
||||
(void)aTimeout;
|
||||
return OT_ERROR_NONE;
|
||||
}
|
||||
|
||||
uint32_t utilsFlashWrite(uint32_t aAddress, uint8_t *aData, uint32_t aSize)
|
||||
{
|
||||
uint32_t ret = 0;
|
||||
uint32_t index = 0;
|
||||
uint8_t byte;
|
||||
|
||||
otEXPECT(sFlashFd >= 0 && aAddress < FLASH_SIZE);
|
||||
|
||||
for (index = 0; index < aSize; index++)
|
||||
{
|
||||
otEXPECT((ret = utilsFlashRead(aAddress + index, &byte, 1)) == 1);
|
||||
// Use bitwise AND to emulate the behavior of flash memory
|
||||
byte &= aData[index];
|
||||
otEXPECT((ret = (uint32_t)pwrite(sFlashFd, &byte, 1, (off_t)(aAddress + index))) == 1);
|
||||
}
|
||||
|
||||
exit:
|
||||
return index;
|
||||
}
|
||||
|
||||
uint32_t utilsFlashRead(uint32_t aAddress, uint8_t *aData, uint32_t aSize)
|
||||
{
|
||||
uint32_t ret = 0;
|
||||
|
||||
otEXPECT(sFlashFd >= 0 && aAddress < FLASH_SIZE);
|
||||
ret = (uint32_t)pread(sFlashFd, aData, aSize, (off_t)aAddress);
|
||||
|
||||
exit:
|
||||
return ret;
|
||||
}
|
||||
@@ -0,0 +1,129 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 flash interface used by settings.cpp.
|
||||
*/
|
||||
|
||||
#ifndef UTILS_FLASH_H
|
||||
#define UTILS_FLASH_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#include <openthread/types.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Perform any initialization for flash driver.
|
||||
*
|
||||
* @retval ::OT_ERROR_NONE Initialize flash driver success.
|
||||
* @retval ::OT_ERROR_FAILED Initialize flash driver fail.
|
||||
*/
|
||||
otError utilsFlashInit(void);
|
||||
|
||||
/**
|
||||
* Get the size of flash that can be read/write by the caller.
|
||||
* The usable flash size is always the multiple of flash page size.
|
||||
*
|
||||
* @returns The size of the flash.
|
||||
*/
|
||||
uint32_t utilsFlashGetSize(void);
|
||||
|
||||
/**
|
||||
* Erase one flash page that include the input address.
|
||||
* This is a non-blocking function. It can work with utilsFlashStatusWait to check when erase is done.
|
||||
*
|
||||
* The flash address starts from 0, and this function maps the input address to the physical address of flash for
|
||||
* erasing. 0 is always mapped to the beginning of one flash page. The input address should never be mapped to the
|
||||
* firmware space or any other protected flash space.
|
||||
*
|
||||
* @param[in] aAddress The start address of the flash to erase.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Erase flash operation is started.
|
||||
* @retval OT_ERROR_FAILED Erase flash operation is not started.
|
||||
* @retval OT_ERROR_INVALID_ARGS aAddress is out of range of flash or not aligend.
|
||||
*/
|
||||
otError utilsFlashErasePage(uint32_t aAddress);
|
||||
|
||||
/**
|
||||
* Check whether flash is ready or busy.
|
||||
*
|
||||
* @param[in] aTimeout The interval in milliseconds waiting for the flash operation to be done and become ready again.
|
||||
* zero indicates that it is a polling function, and returns current status of flash immediately.
|
||||
* non-zero indicates that it is blocking there until the operation is done and become ready, or
|
||||
* timeout expires.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Flash is ready for any operation.
|
||||
* @retval OT_ERROR_BUSY Flash is busy.
|
||||
*/
|
||||
otError utilsFlashStatusWait(uint32_t aTimeout);
|
||||
|
||||
/**
|
||||
* Write flash. The write operation only clears bits, but never set bits.
|
||||
*
|
||||
* The flash address starts from 0, and this function maps the input address to the physical address of flash for
|
||||
* writing. 0 is always mapped to the beginning of one flash page. The input address should never be mapped to the
|
||||
* firmware space or any other protected flash space.
|
||||
*
|
||||
* @param[in] aAddress The start address of the flash to write.
|
||||
* @param[in] aData The pointer of the data to write.
|
||||
* @param[in] aSize The size of the data to write.
|
||||
*
|
||||
* @returns The actual size of octets write to flash.
|
||||
* It is expected the same as aSize, and may be less than aSize.
|
||||
* 0 indicates that something wrong happens when writing.
|
||||
*/
|
||||
uint32_t utilsFlashWrite(uint32_t aAddress, uint8_t *aData, uint32_t aSize);
|
||||
|
||||
/**
|
||||
* Read flash.
|
||||
*
|
||||
* The flash address starts from 0, and this function maps the input address to the physical address of flash for
|
||||
* reading. 0 is always mapped to the beginning of one flash page. The input address should never be mapped to the
|
||||
* firmware space or any other protected flash space.
|
||||
*
|
||||
* @param[in] aAddress The start address of the flash to read.
|
||||
* @param[Out] aData The pointer of buffer for reading.
|
||||
* @param[in] aSize The size of the data to read.
|
||||
*
|
||||
* @returns The actual size of octets read to buffer.
|
||||
* It is expected the same as aSize, and may be less than aSize.
|
||||
* 0 indicates that something wrong happens when reading.
|
||||
*/
|
||||
uint32_t utilsFlashRead(uint32_t aAddress, uint8_t *aData, uint32_t aSize);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // extern "C"
|
||||
#endif
|
||||
|
||||
#endif // UTILS_FLASH_H
|
||||
@@ -0,0 +1,239 @@
|
||||
/*
|
||||
* Copyright (c) 2018, The OpenThread Authors.
|
||||
* 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 includes implementation of frame queue.
|
||||
*/
|
||||
|
||||
#include "platform-posix.h"
|
||||
|
||||
#include "frame_queue.hpp"
|
||||
|
||||
#include <assert.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "code_utils.h"
|
||||
|
||||
namespace ot {
|
||||
|
||||
otError FrameQueue::Push(const uint8_t *aFrame, uint8_t aLength)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
uint16_t newTail = mTail + aLength + 1;
|
||||
|
||||
assert(aFrame != NULL);
|
||||
otEXPECT_ACTION(aFrame != NULL, error = OT_ERROR_INVALID_ARGS);
|
||||
|
||||
if (mHead > mTail)
|
||||
{
|
||||
otEXPECT_ACTION(newTail < mHead, error = OT_ERROR_NO_BUFS);
|
||||
}
|
||||
else if (newTail >= sizeof(mBuffer))
|
||||
{
|
||||
newTail -= sizeof(mBuffer);
|
||||
otEXPECT_ACTION(newTail < mHead, error = OT_ERROR_NO_BUFS);
|
||||
}
|
||||
|
||||
mBuffer[mTail] = aLength;
|
||||
|
||||
if (newTail > mTail)
|
||||
{
|
||||
memcpy(mBuffer + mTail + 1, aFrame, aLength);
|
||||
}
|
||||
else
|
||||
{
|
||||
uint16_t half = (sizeof(mBuffer) - mTail - 1);
|
||||
memcpy(mBuffer + mTail + 1, aFrame, half);
|
||||
memcpy(mBuffer, aFrame + half, (aLength - half));
|
||||
}
|
||||
|
||||
mTail = newTail;
|
||||
|
||||
exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
void FrameQueue::Shift(void)
|
||||
{
|
||||
if (mHead != mTail)
|
||||
{
|
||||
mHead += 1 + mBuffer[mHead];
|
||||
mHead %= sizeof(mBuffer);
|
||||
}
|
||||
}
|
||||
|
||||
const uint8_t *FrameQueue::Peek(uint8_t *aFrame, uint8_t &aLength)
|
||||
{
|
||||
const uint8_t *frame = NULL;
|
||||
uint16_t next;
|
||||
|
||||
otEXPECT(mHead != mTail);
|
||||
|
||||
aLength = mBuffer[mHead];
|
||||
next = mHead + 1 + aLength;
|
||||
|
||||
if (next >= sizeof(mBuffer))
|
||||
{
|
||||
uint16_t half = sizeof(mBuffer) - mHead - 1;
|
||||
memcpy(aFrame, mBuffer + mHead + 1, half);
|
||||
memcpy(aFrame + half, mBuffer, aLength - half);
|
||||
frame = aFrame;
|
||||
}
|
||||
else
|
||||
{
|
||||
frame = mBuffer + mHead + 1;
|
||||
}
|
||||
|
||||
exit:
|
||||
return frame;
|
||||
}
|
||||
|
||||
} // namespace ot
|
||||
|
||||
#if SELF_TEST
|
||||
#include <stdlib.h>
|
||||
void TestSingle()
|
||||
{
|
||||
otError error;
|
||||
ot::FrameQueue frameQueue;
|
||||
uint8_t length;
|
||||
uint8_t frame[255];
|
||||
|
||||
for (size_t i = 0; i < sizeof(frame); ++i)
|
||||
{
|
||||
frame[i] = i;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < sizeof(frame); ++i)
|
||||
{
|
||||
uint8_t outFrame[255];
|
||||
const uint8_t *retFrame = NULL;
|
||||
error = frameQueue.Push(frame, i);
|
||||
assert(OT_ERROR_NONE == error);
|
||||
assert(!frameQueue.IsEmpty());
|
||||
retFrame = frameQueue.Peek(outFrame, length);
|
||||
assert(retFrame != NULL);
|
||||
assert(length == i);
|
||||
|
||||
for (size_t j = 0; j < i; ++j)
|
||||
{
|
||||
assert(retFrame[j] == frame[j]);
|
||||
}
|
||||
|
||||
frameQueue.Shift();
|
||||
assert(frameQueue.IsEmpty());
|
||||
}
|
||||
}
|
||||
|
||||
void TestMultiple()
|
||||
{
|
||||
otError error;
|
||||
ot::FrameQueue frameQueue;
|
||||
uint8_t length;
|
||||
uint8_t frame[255];
|
||||
|
||||
for (size_t i = 0; i < sizeof(frame); ++i)
|
||||
{
|
||||
frame[i] = i;
|
||||
}
|
||||
|
||||
srand(0);
|
||||
|
||||
for (size_t i = 0; i < sizeof(frame); ++i)
|
||||
{
|
||||
uint8_t outFrame[255];
|
||||
const uint8_t *retFrame = NULL;
|
||||
|
||||
int action = rand();
|
||||
if (action & 0x01) // push when odd
|
||||
{
|
||||
error = frameQueue.Push(frame, i);
|
||||
if (error == OT_ERROR_NO_BUFS)
|
||||
continue;
|
||||
|
||||
assert(OT_ERROR_NONE == error);
|
||||
assert(!frameQueue.IsEmpty());
|
||||
retFrame = frameQueue.Peek(outFrame, length);
|
||||
assert(retFrame != NULL);
|
||||
|
||||
for (size_t j = 0; j < length; ++j)
|
||||
{
|
||||
assert(retFrame[j] == frame[j]);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
frameQueue.Shift();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void TestRing()
|
||||
{
|
||||
ot::FrameQueue frameQueue;
|
||||
uint8_t length;
|
||||
uint8_t frame[255];
|
||||
|
||||
for (size_t i = 0; i < sizeof(frame); ++i)
|
||||
{
|
||||
frame[i] = i;
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < OPENTHREAD_CONFIG_FRAME_CACHE_SIZE + 255; i += sizeof(frame))
|
||||
{
|
||||
uint8_t outFrame[255];
|
||||
const uint8_t *retFrame = NULL;
|
||||
|
||||
frameQueue.Push(frame, sizeof(frame));
|
||||
|
||||
retFrame = frameQueue.Peek(outFrame, length);
|
||||
|
||||
for (size_t j = 0; j < sizeof(frame); ++j)
|
||||
{
|
||||
assert(retFrame[j] == frame[j]);
|
||||
}
|
||||
|
||||
frameQueue.Shift();
|
||||
};
|
||||
}
|
||||
|
||||
void RunAllTests()
|
||||
{
|
||||
TestSingle();
|
||||
TestMultiple();
|
||||
TestRing();
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
RunAllTests();
|
||||
printf("All tests passed\n");
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
@@ -0,0 +1,117 @@
|
||||
/*
|
||||
* Copyright (c) 2018, The OpenThread Authors.
|
||||
* 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 includes definitions for frame queue.
|
||||
*/
|
||||
|
||||
#ifndef OT_FRAME_QUEUE_HPP_
|
||||
#define OT_FRAME_QUEUE_HPP_
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
/**
|
||||
* @def OPENTHREAD_CONFIG_FRAME_QUEUE_SIZE
|
||||
*
|
||||
* The size of a frame queue in bytes.
|
||||
*
|
||||
*/
|
||||
#ifndef OPENTHREAD_CONFIG_FRAME_QUEUE_SIZE
|
||||
#define OPENTHREAD_CONFIG_FRAME_QUEUE_SIZE 4096
|
||||
#endif
|
||||
|
||||
namespace ot {
|
||||
|
||||
class FrameQueue
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* This constructor initializes a frame queue based on ring buffer.
|
||||
*
|
||||
*/
|
||||
FrameQueue(void)
|
||||
: mHead(0)
|
||||
, mTail(0)
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* This method checks if the cache is empty.
|
||||
*
|
||||
* @retval true No frames are queued.
|
||||
* @retval false At least one frame is queued.
|
||||
*
|
||||
*/
|
||||
bool IsEmpty(void) const { return mHead == mTail; }
|
||||
|
||||
/**
|
||||
* This method removes one frame from the head.
|
||||
*
|
||||
*/
|
||||
void Shift(void);
|
||||
|
||||
/**
|
||||
* This method pushes one frame into the queue.
|
||||
*
|
||||
* @param[in] aFrame A pointer to a spinel frame to be queued.
|
||||
* @param[in] aLength Frame length in bytes.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully queued this frame.
|
||||
* @retval OT_ERROR_NO_BUFS Insufficient memory for this frame.
|
||||
*
|
||||
*/
|
||||
otError Push(const uint8_t *aFrame, uint8_t aLength);
|
||||
|
||||
/**
|
||||
* This method gets one frame at head.
|
||||
*
|
||||
* @note aFrame is only used when necessary, always use the returned pointer to access frame data.
|
||||
*
|
||||
* @param[out] aFrame A pointer to the frame to receive the data.
|
||||
* @param[out] aLength A reference to receive the frame length.
|
||||
*
|
||||
* @return A pointer to the frame.
|
||||
*
|
||||
*/
|
||||
const uint8_t *Peek(uint8_t *aFrame, uint8_t &aLength);
|
||||
|
||||
private:
|
||||
enum
|
||||
{
|
||||
kQueueSize = OPENTHREAD_CONFIG_FRAME_QUEUE_SIZE,
|
||||
};
|
||||
|
||||
uint8_t mBuffer[kQueueSize];
|
||||
uint16_t mHead;
|
||||
uint16_t mTail;
|
||||
};
|
||||
|
||||
} // namespace ot
|
||||
|
||||
#endif // OT_FRAME_CACHE_HPP_
|
||||
Symlink
+1
@@ -0,0 +1 @@
|
||||
../../ncp/hdlc.cpp
|
||||
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 "platform-posix.h"
|
||||
#include <openthread-core-config.h>
|
||||
#include <openthread/config.h>
|
||||
|
||||
#include <ctype.h>
|
||||
#include <inttypes.h>
|
||||
#include <stdarg.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <syslog.h>
|
||||
|
||||
#include <openthread/platform/logging.h>
|
||||
|
||||
#include "code_utils.h"
|
||||
|
||||
// Macro to append content to end of the log string.
|
||||
|
||||
#define LOG_PRINTF(...) \
|
||||
charsWritten = snprintf(&logString[offset], sizeof(logString) - offset, __VA_ARGS__); \
|
||||
otEXPECT_ACTION(charsWritten >= 0, logString[offset] = 0); \
|
||||
offset += (unsigned int)charsWritten; \
|
||||
otEXPECT_ACTION(offset < sizeof(logString), logString[sizeof(logString) - 1] = 0)
|
||||
|
||||
#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_PLATFORM_DEFINED) || \
|
||||
(OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_NCP_SPINEL)
|
||||
OT_TOOL_WEAK void otPlatLog(otLogLevel aLogLevel, otLogRegion aLogRegion, const char *aFormat, ...)
|
||||
{
|
||||
char logString[512];
|
||||
unsigned int offset;
|
||||
int charsWritten;
|
||||
va_list args;
|
||||
|
||||
offset = 0;
|
||||
|
||||
LOG_PRINTF("[%" PRIx64 "] ", NODE_ID);
|
||||
|
||||
va_start(args, aFormat);
|
||||
charsWritten = vsnprintf(&logString[offset], sizeof(logString) - offset, aFormat, args);
|
||||
va_end(args);
|
||||
|
||||
otEXPECT_ACTION(charsWritten >= 0, logString[offset] = 0);
|
||||
|
||||
exit:
|
||||
#ifndef _WIN32
|
||||
syslog(LOG_CRIT, "%s", logString);
|
||||
#else
|
||||
printf("%s\r\n", logString);
|
||||
#endif
|
||||
|
||||
(void)aLogLevel;
|
||||
(void)aLogRegion;
|
||||
}
|
||||
|
||||
#endif // #if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_PLATFORM_DEFINED)
|
||||
@@ -0,0 +1,112 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 "platform-posix.h"
|
||||
|
||||
#include <unistd.h>
|
||||
|
||||
#include <openthread/types.h>
|
||||
#include <openthread/platform/misc.h>
|
||||
|
||||
#include "platform.h"
|
||||
|
||||
extern int gArgumentsCount;
|
||||
extern char **gArguments;
|
||||
|
||||
static otPlatResetReason sPlatResetReason = OT_PLAT_RESET_REASON_POWER_ON;
|
||||
bool gPlatformPseudoResetWasRequested;
|
||||
static otPlatMcuPowerState gPlatMcuPowerState = OT_PLAT_MCU_POWER_STATE_ON;
|
||||
|
||||
void otPlatReset(otInstance *aInstance)
|
||||
{
|
||||
#if OPENTHREAD_PLATFORM_USE_PSEUDO_RESET
|
||||
gPlatformPseudoResetWasRequested = true;
|
||||
sPlatResetReason = OT_PLAT_RESET_REASON_SOFTWARE;
|
||||
|
||||
#else // elif OPENTHREAD_PLATFORM_USE_PSEUDO_RESET
|
||||
// Restart the process using execvp.
|
||||
char *argv[gArgumentsCount + 1];
|
||||
|
||||
for (int i = 0; i < gArgumentsCount; ++i)
|
||||
{
|
||||
argv[i] = gArguments[i];
|
||||
}
|
||||
|
||||
argv[gArgumentsCount] = NULL;
|
||||
|
||||
PlatformDeinit();
|
||||
platformUartRestore();
|
||||
|
||||
alarm(0);
|
||||
|
||||
execvp(argv[0], argv);
|
||||
perror("reset failed");
|
||||
exit(EXIT_FAILURE);
|
||||
|
||||
#endif // else OPENTHREAD_PLATFORM_USE_PSEUDO_RESET
|
||||
|
||||
(void)aInstance;
|
||||
}
|
||||
|
||||
otPlatResetReason otPlatGetResetReason(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
return sPlatResetReason;
|
||||
}
|
||||
|
||||
void otPlatWakeHost(void)
|
||||
{
|
||||
// TODO: implement an operation to wake the host from sleep state.
|
||||
}
|
||||
|
||||
otError otPlatSetMcuPowerState(otInstance *aInstance, otPlatMcuPowerState aState)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
|
||||
(void)aInstance;
|
||||
|
||||
switch (aState)
|
||||
{
|
||||
case OT_PLAT_MCU_POWER_STATE_ON:
|
||||
case OT_PLAT_MCU_POWER_STATE_LOW_POWER:
|
||||
gPlatMcuPowerState = aState;
|
||||
break;
|
||||
|
||||
default:
|
||||
error = OT_ERROR_FAILED;
|
||||
break;
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
otPlatMcuPowerState otPlatGetMcuPowerState(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
return gPlatMcuPowerState;
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
* Copyright (c) 2017, The OpenThread Authors.
|
||||
* 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 includes posix compile-time configuration constants
|
||||
* for OpenThread.
|
||||
*/
|
||||
|
||||
#ifndef OPENTHREAD_CORE_POSIX_CONFIG_H_
|
||||
#define OPENTHREAD_CORE_POSIX_CONFIG_H_
|
||||
|
||||
/**
|
||||
* @def OPENTHREAD_CONFIG_PLATFORM_INFO
|
||||
*
|
||||
* The platform-specific string to insert into the OpenThread version string.
|
||||
*
|
||||
*/
|
||||
#define OPENTHREAD_CONFIG_PLATFORM_INFO "POSIX"
|
||||
|
||||
/**
|
||||
* @def OPENTHREAD_CONFIG_LOG_OUTPUT
|
||||
*
|
||||
* Specify where the log output should go.
|
||||
*
|
||||
*/
|
||||
#ifndef OPENTHREAD_CONFIG_LOG_OUTPUT /* allow command line override */
|
||||
#define OPENTHREAD_CONFIG_LOG_OUTPUT OPENTHREAD_CONFIG_LOG_OUTPUT_PLATFORM_DEFINED
|
||||
#endif
|
||||
|
||||
#if OPENTHREAD_RADIO
|
||||
/**
|
||||
* @def OPENTHREAD_CONFIG_ENABLE_SOFTWARE_ACK_TIMEOUT
|
||||
*
|
||||
* Define to 1 if you want to enable software ACK timeout logic.
|
||||
*
|
||||
*/
|
||||
#define OPENTHREAD_CONFIG_ENABLE_SOFTWARE_ACK_TIMEOUT 1
|
||||
|
||||
/**
|
||||
* @def OPENTHREAD_CONFIG_ENABLE_SOFTWARE_RETRANSMIT
|
||||
*
|
||||
* Define to 1 if you want to enable software retransmission logic.
|
||||
*
|
||||
* Applicable only if raw link layer API is enabled (i.e., `OPENTHREAD_ENABLE_RAW_LINK_API` is set).
|
||||
*
|
||||
*/
|
||||
#define OPENTHREAD_CONFIG_ENABLE_SOFTWARE_RETRANSMIT 1
|
||||
#endif // OPENTHREAD_RADIO
|
||||
|
||||
/**
|
||||
* @def OPENTHREAD_CONFIG_ENABLE_PLATFORM_USEC_TIMER
|
||||
*
|
||||
* Define to 1 if you want to support microsecond timer in platform.
|
||||
*
|
||||
*/
|
||||
#define OPENTHREAD_CONFIG_ENABLE_PLATFORM_USEC_TIMER 1
|
||||
|
||||
#endif // OPENTHREAD_CORE_POSIX_CONFIG_H_
|
||||
@@ -0,0 +1,213 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 includes the (posix or windows) platform-specific initializers.
|
||||
*/
|
||||
|
||||
#ifndef PLATFORM_POSIX_H_
|
||||
#define PLATFORM_POSIX_H_
|
||||
|
||||
#include <openthread-core-config.h>
|
||||
#include <openthread/config.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
#include <arpa/inet.h>
|
||||
#include <fcntl.h>
|
||||
#include <netinet/in.h>
|
||||
#include <poll.h>
|
||||
#include <sys/select.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <openthread/openthread.h>
|
||||
|
||||
#include "openthread-core-config.h"
|
||||
|
||||
enum
|
||||
{
|
||||
OT_SIM_EVENT_ALARM_FIRED = 0,
|
||||
OT_SIM_EVENT_RADIO_RECEIVED = 1,
|
||||
OT_EVENT_DATA_MAX_SIZE = 1024,
|
||||
};
|
||||
|
||||
OT_TOOL_PACKED_BEGIN
|
||||
struct Event
|
||||
{
|
||||
uint64_t mDelay;
|
||||
uint8_t mEvent;
|
||||
uint16_t mDataLength;
|
||||
uint8_t mData[OT_EVENT_DATA_MAX_SIZE];
|
||||
} OT_TOOL_PACKED_END;
|
||||
|
||||
/**
|
||||
* Unique node ID.
|
||||
*
|
||||
*/
|
||||
extern uint64_t NODE_ID;
|
||||
|
||||
/**
|
||||
* Well-known Unique ID used by a simulated radio that supports promiscuous mode.
|
||||
*
|
||||
*/
|
||||
#define WELLKNOWN_NODE_ID 34
|
||||
|
||||
/**
|
||||
* This function initializes the alarm service used by OpenThread.
|
||||
*
|
||||
*/
|
||||
void platformAlarmInit(uint32_t aSpeedUpFactor);
|
||||
|
||||
/**
|
||||
* This function retrieves the time remaining until the alarm fires.
|
||||
*
|
||||
* @param[out] aTimeval A pointer to the timeval struct.
|
||||
*
|
||||
*/
|
||||
void platformAlarmUpdateTimeout(struct timeval *tv);
|
||||
|
||||
/**
|
||||
* This function performs alarm driver processing.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
*
|
||||
*/
|
||||
void platformAlarmProcess(otInstance *aInstance);
|
||||
|
||||
/**
|
||||
* This function returns the next alarm event time.
|
||||
*
|
||||
* @returns The next alarm fire time.
|
||||
*
|
||||
*/
|
||||
int32_t platformAlarmGetNext(void);
|
||||
|
||||
/**
|
||||
* This function returns the current alarm time.
|
||||
*
|
||||
* @returns The current alarm time.
|
||||
*
|
||||
*/
|
||||
uint64_t platformAlarmGetNow(void);
|
||||
|
||||
/**
|
||||
* This function advances the alarm time by @p aDelta.
|
||||
*
|
||||
* @param[in] aDelta The amount of time to advance.
|
||||
*
|
||||
*/
|
||||
void platformAlarmAdvanceNow(uint64_t aDelta);
|
||||
|
||||
/**
|
||||
* This function initializes the radio service used by OpenThread.
|
||||
*
|
||||
* @param[in] aRadioFile A pointer to the radio file.
|
||||
* @param[in] aRadioConfig A pointer to the radio config.
|
||||
*
|
||||
*/
|
||||
void platformRadioInit(const char *aRadioFile, const char *aRadioConfig);
|
||||
|
||||
/**
|
||||
* This function shuts down the radio service used by OpenThread.
|
||||
*
|
||||
*/
|
||||
void platformRadioDeinit(void);
|
||||
|
||||
/**
|
||||
* This function inputs a received radio frame.
|
||||
*
|
||||
* @param[in] aInstance A pointer to the OpenThread instance.
|
||||
* @param[in] aBuf A pointer to the received radio frame.
|
||||
* @param[in] aBufLength The size of the received radio frame.
|
||||
*
|
||||
*/
|
||||
void platformRadioReceive(otInstance *aInstance, uint8_t *aBuf, uint16_t aBufLength);
|
||||
|
||||
/**
|
||||
* This function updates the file descriptor sets with file descriptors used by the radio driver.
|
||||
*
|
||||
* @param[inout] aReadFdSet A pointer to the read file descriptors.
|
||||
* @param[inout] aWriteFdSet A pointer to the write file descriptors.
|
||||
* @param[inout] aMaxFd A pointer to the max file descriptor.
|
||||
* @param[inout] aTimeout A pointer to the timeout.
|
||||
*
|
||||
*/
|
||||
void platformRadioUpdateFdSet(fd_set *aReadFdSet, fd_set *aWriteFdSet, int *aMaxFd, struct timeval *aTimeout);
|
||||
|
||||
/**
|
||||
* This function performs radio driver processing.
|
||||
*
|
||||
* @param[in] aInstance A pointer to the OpenThread instance.
|
||||
* @param[in] aReadFdSet A pointer to the read file descriptors.
|
||||
* @param[in] aWriteFdSet A pointer to the write file descriptors.
|
||||
*
|
||||
*/
|
||||
void platformRadioProcess(otInstance *aInstance, fd_set *aReadFdSet, fd_set *aWriteFdSet);
|
||||
|
||||
/**
|
||||
* This function initializes the random number service used by OpenThread.
|
||||
*
|
||||
*/
|
||||
void platformRandomInit(void);
|
||||
|
||||
/**
|
||||
* This function updates the file descriptor sets with file descriptors used by the UART driver.
|
||||
*
|
||||
* @param[inout] aReadFdSet A pointer to the read file descriptors.
|
||||
* @param[inout] aWriteFdSet A pointer to the write file descriptors.
|
||||
* @param[inout] aMaxFd A pointer to the max file descriptor.
|
||||
*
|
||||
*/
|
||||
void platformUartUpdateFdSet(fd_set *aReadFdSet, fd_set *aWriteFdSet, fd_set *aErrorFdSet, int *aMaxFd);
|
||||
|
||||
/**
|
||||
* This function performs radio driver processing.
|
||||
*
|
||||
* @param[in] aReadFdSet A pointer to the read file descriptors.
|
||||
* @param[in] aWriteFdSet A pointer to the write file descriptors.
|
||||
* @param[in] aErrorFdSet A pointer to the error file descriptors.
|
||||
*
|
||||
*/
|
||||
void platformUartProcess(const fd_set *aReadFdSet, const fd_set *aWriteFdSet, const fd_set *aErrorFdSet);
|
||||
|
||||
/**
|
||||
* This function restores the Uart.
|
||||
*
|
||||
*/
|
||||
void platformUartRestore(void);
|
||||
|
||||
#endif // PLATFORM_POSIX_H_
|
||||
@@ -0,0 +1,162 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 includes the platform-specific initializers.
|
||||
*/
|
||||
|
||||
#include "platform-posix.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
#include <libgen.h>
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <syslog.h>
|
||||
|
||||
#include <openthread/openthread.h>
|
||||
#include <openthread/tasklet.h>
|
||||
#include <openthread/platform/alarm-milli.h>
|
||||
|
||||
uint64_t NODE_ID = 0;
|
||||
|
||||
extern bool gPlatformPseudoResetWasRequested;
|
||||
|
||||
int gArgumentsCount = 0;
|
||||
char **gArguments = NULL;
|
||||
|
||||
void PrintUsage(const char *aArg0)
|
||||
{
|
||||
fprintf(stderr, "Syntax:\n %s [-s TimeSpeedUpFactor] {NodeId|Device DeviceConfig|Command CommandArgs}\n", aArg0);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
void PlatformInit(int aArgCount, char *aArgVector[])
|
||||
{
|
||||
int i;
|
||||
uint32_t speedUpFactor = 1;
|
||||
char * endptr;
|
||||
const char *radioFile = NULL;
|
||||
const char *radioConfig = "";
|
||||
|
||||
if (gPlatformPseudoResetWasRequested)
|
||||
{
|
||||
gPlatformPseudoResetWasRequested = false;
|
||||
return;
|
||||
}
|
||||
|
||||
if (aArgCount < 2)
|
||||
{
|
||||
PrintUsage(aArgVector[0]);
|
||||
}
|
||||
|
||||
i = 1;
|
||||
if (!strcmp(aArgVector[i], "-s"))
|
||||
{
|
||||
++i;
|
||||
speedUpFactor = (uint32_t)strtol(aArgVector[i], &endptr, 0);
|
||||
|
||||
if (*endptr != '\0' || speedUpFactor == 0)
|
||||
{
|
||||
fprintf(stderr, "Invalid value for TimerSpeedUpFactor: %s\n", aArgVector[i]);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
++i;
|
||||
}
|
||||
|
||||
if (i >= aArgCount)
|
||||
{
|
||||
PrintUsage(aArgVector[0]);
|
||||
}
|
||||
|
||||
radioFile = aArgVector[i];
|
||||
if (i + 1 < aArgCount)
|
||||
{
|
||||
radioConfig = aArgVector[i + 1];
|
||||
}
|
||||
|
||||
openlog(basename(aArgVector[0]), LOG_PID, LOG_USER);
|
||||
setlogmask(setlogmask(0) & LOG_UPTO(LOG_NOTICE));
|
||||
|
||||
gArgumentsCount = aArgCount;
|
||||
gArguments = aArgVector;
|
||||
|
||||
platformAlarmInit(speedUpFactor);
|
||||
platformRadioInit(radioFile, radioConfig);
|
||||
platformRandomInit();
|
||||
}
|
||||
|
||||
bool PlatformPseudoResetWasRequested(void)
|
||||
{
|
||||
return gPlatformPseudoResetWasRequested;
|
||||
}
|
||||
|
||||
void PlatformDeinit(void)
|
||||
{
|
||||
platformRadioDeinit();
|
||||
}
|
||||
|
||||
void PlatformProcessDrivers(otInstance *aInstance)
|
||||
{
|
||||
fd_set read_fds;
|
||||
fd_set write_fds;
|
||||
fd_set error_fds;
|
||||
struct timeval timeout;
|
||||
int max_fd = -1;
|
||||
int rval;
|
||||
|
||||
FD_ZERO(&read_fds);
|
||||
FD_ZERO(&write_fds);
|
||||
FD_ZERO(&error_fds);
|
||||
|
||||
platformAlarmUpdateTimeout(&timeout);
|
||||
platformUartUpdateFdSet(&read_fds, &write_fds, &error_fds, &max_fd);
|
||||
platformRadioUpdateFdSet(&read_fds, &write_fds, &max_fd, &timeout);
|
||||
|
||||
if (otTaskletsArePending(aInstance))
|
||||
{
|
||||
timeout.tv_sec = 0;
|
||||
timeout.tv_usec = 0;
|
||||
}
|
||||
|
||||
rval = select(max_fd + 1, &read_fds, &write_fds, &error_fds, &timeout);
|
||||
|
||||
if ((rval < 0) && (errno != EINTR))
|
||||
{
|
||||
perror("select");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
platformUartProcess(&read_fds, &write_fds, &error_fds);
|
||||
platformRadioProcess(aInstance, &read_fds, &write_fds);
|
||||
platformAlarmProcess(aInstance);
|
||||
}
|
||||
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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-specific initializers.
|
||||
*/
|
||||
|
||||
#ifndef PLATFORM_H_
|
||||
#define PLATFORM_H_
|
||||
|
||||
#include <openthread/types.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* This function performs all platform-specific initialization.
|
||||
*
|
||||
*/
|
||||
void PlatformInit(int argc, char *argv[]);
|
||||
|
||||
/**
|
||||
* This function performs all platform-specific deinitialization.
|
||||
*
|
||||
*/
|
||||
void PlatformDeinit(void);
|
||||
|
||||
/**
|
||||
* This function returns true is a pseudo-reset was requested.
|
||||
* In such a case, the main loop should shut down and re-initialize
|
||||
* the OpenThread instance.
|
||||
*
|
||||
*/
|
||||
bool PlatformPseudoResetWasRequested(void);
|
||||
|
||||
/**
|
||||
* This function performs all platform-specific processing.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
*
|
||||
*/
|
||||
void PlatformProcessDrivers(otInstance *aInstance);
|
||||
|
||||
/**
|
||||
* This function is called whenever platform drivers needs processing.
|
||||
*
|
||||
*/
|
||||
extern void PlatformEventSignalPending(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // end of extern "C"
|
||||
#endif
|
||||
|
||||
#endif // PLATFORM_H_
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,492 @@
|
||||
/*
|
||||
* Copyright (c) 2018, The OpenThread Authors.
|
||||
* 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 includes definitions for the spinel based radio transceiver.
|
||||
*/
|
||||
|
||||
#ifndef RADIO_SPINEL_HPP_
|
||||
#define RADIO_SPINEL_HPP_
|
||||
|
||||
#include "frame_queue.hpp"
|
||||
#include "hdlc.hpp"
|
||||
#include "spinel.h"
|
||||
|
||||
namespace ot {
|
||||
|
||||
class RadioSpinel
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* This constructor initializes the spinel based OpenThread transceiver.
|
||||
*
|
||||
*/
|
||||
RadioSpinel(void);
|
||||
|
||||
/**
|
||||
* Initialize this radio transceiver.
|
||||
*
|
||||
* @param[in] aRadioFile The path to either a uart device or an executable.
|
||||
* @param[in] aRadioConfig Parameters given to the device or executable.
|
||||
*
|
||||
*/
|
||||
void Init(const char *aRadioFile, const char *aRadioConfig);
|
||||
|
||||
/**
|
||||
* Deinitialize this radio transceiver.
|
||||
*
|
||||
*/
|
||||
void Deinit(void);
|
||||
|
||||
/**
|
||||
* This method gets the status of promiscuous mode.
|
||||
*
|
||||
* @retval true Promiscuous mode is enabled.
|
||||
* @retval false Promiscuous mode is disabled.
|
||||
*
|
||||
*/
|
||||
bool GetPromiscuous(void) const { return mPromiscuous; }
|
||||
|
||||
/**
|
||||
* This method sets the status of promiscuous mode.
|
||||
*
|
||||
* @param[in] aEnable Whether to enable or disable promiscuous mode.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError SetPromiscuous(bool aEnable);
|
||||
|
||||
/**
|
||||
* This method sets the Short Address for address filtering.
|
||||
*
|
||||
* @param[in] aShortAddress The IEEE 802.15.4 Short Address.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError SetShortAddress(uint16_t aAddress);
|
||||
|
||||
/**
|
||||
* This method gets the factory-assigned IEEE EUI-64 for this transceiver.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
* @param[out] aIeeeEui64 A pointer to the factory-assigned IEEE EUI-64.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError GetIeeeEui64(uint8_t *aIeeeEui64);
|
||||
|
||||
/**
|
||||
* This method sets the Extended Address for address filtering.
|
||||
*
|
||||
* @param[in] aExtAddress A pointer to the IEEE 802.15.4 Extended Address stored in little-endian byte order.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError SetExtendedAddress(const otExtAddress &aAddress);
|
||||
|
||||
/**
|
||||
* This method sets the PAN ID for address filtering.
|
||||
*
|
||||
* @param[in] aPanId The IEEE 802.15.4 PAN ID.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError SetPanId(uint16_t aPanId);
|
||||
|
||||
/**
|
||||
* This method gets the radio's transmit power in dBm.
|
||||
*
|
||||
* @param[out] aPower The transmit power in dBm.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError GetTransmitPower(int8_t &aPower);
|
||||
|
||||
/**
|
||||
* This method sets the radio's transmit power in dBm.
|
||||
*
|
||||
* @param[in] aPower The transmit power in dBm.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError SetTransmitPower(int8_t aPower);
|
||||
|
||||
/**
|
||||
* This method returns the radio receive sensitivity value.
|
||||
*
|
||||
* @returns The radio receive sensitivity value in dBm.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
uint8_t GetReceiveSensitivity(void) const { return mRxSensitivity; }
|
||||
|
||||
/**
|
||||
* This method returns a reference to the transmit buffer.
|
||||
*
|
||||
* The caller forms the IEEE 802.15.4 frame in this buffer then calls otPlatRadioTransmit() to request transmission.
|
||||
*
|
||||
* @returns A reference to the transmit buffer.
|
||||
*
|
||||
*/
|
||||
otRadioFrame &GetTransmitFrame(void) { return mTxRadioFrame; }
|
||||
|
||||
/**
|
||||
* This method enables or disables source address match feature.
|
||||
*
|
||||
* @param[in] aEnable Enable/disable source address match feature.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError EnableSrcMatch(bool aEnable);
|
||||
|
||||
/**
|
||||
* This method adds a short address to the source address match table.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
* @param[in] aShortAddress The short address to be added.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully added short address to the source match table.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
* @retval OT_ERROR_NO_BUFS No available entry in the source match table.
|
||||
*/
|
||||
otError AddSrcMatchShortEntry(const uint16_t aShortAddress);
|
||||
|
||||
/**
|
||||
* This method removes a short address from the source address match table.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
* @param[in] aShortAddress The short address to be removed.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully removed short address from the source match table.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
* @retval OT_ERROR_NO_ADDRESS The short address is not in source address match table.
|
||||
*/
|
||||
otError ClearSrcMatchShortEntry(const uint16_t aShortAddress);
|
||||
|
||||
/**
|
||||
* Clear all short addresses from the source address match table.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError ClearSrcMatchShortEntries(void);
|
||||
|
||||
/**
|
||||
* Add an extended address to the source address match table.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
* @param[in] aExtAddress The extended address to be added stored in little-endian byte order.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully added extended address to the source match table.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
* @retval OT_ERROR_NO_BUFS No available entry in the source match table.
|
||||
*/
|
||||
otError AddSrcMatchExtEntry(const otExtAddress &aExtAddress);
|
||||
|
||||
/**
|
||||
* Remove an extended address from the source address match table.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
* @param[in] aExtAddress The extended address to be removed stored in little-endian byte order.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully removed the extended address from the source match table.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
* @retval OT_ERROR_NO_ADDRESS The extended address is not in source address match table.
|
||||
*/
|
||||
otError ClearSrcMatchExtEntry(const otExtAddress &aExtAddress);
|
||||
|
||||
/**
|
||||
* Clear all the extended/long addresses from source address match table.
|
||||
*
|
||||
* @param[in] aInstance The OpenThread instance structure.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Succeeded.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError ClearSrcMatchExtEntries(void);
|
||||
|
||||
/**
|
||||
* This method switches the radio state from Receive to Transmit.
|
||||
*
|
||||
* @param[in] aFrame A reference to the transmitted frame.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully transitioned to Transmit.
|
||||
* @retval OT_ERROR_BUSY Failed due to another transmission is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
* @retval OT_ERROR_INVALID_STATE The radio was not in the Receive state.
|
||||
*/
|
||||
otError Transmit(otRadioFrame &aFrame);
|
||||
|
||||
/**
|
||||
* This method swithes the radio state from Sleep to Receive.
|
||||
*
|
||||
* @param[in] aChannel The channel to use for receiving.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully transitioned to Receive.
|
||||
* @retval OT_ERROR_INVALID_STATE The radio was disabled or transmitting.
|
||||
*
|
||||
*/
|
||||
otError Receive(uint8_t aChannel);
|
||||
|
||||
/**
|
||||
* This method switches the radio state from Receive to Sleep.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully transitioned to Sleep.
|
||||
* @retval OT_ERROR_BUSY The radio was transmitting
|
||||
* @retval OT_ERROR_INVALID_STATE The radio was disabled
|
||||
*
|
||||
*/
|
||||
otError Sleep(void);
|
||||
|
||||
/**
|
||||
* Enable the radio.
|
||||
*
|
||||
* @param[in] aInstance A pointer to the OpenThread instance.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully enabled.
|
||||
* @retval OT_ERROR_FAILED The radio could not be enabled.
|
||||
*
|
||||
*/
|
||||
otError Enable(otInstance *aInstance);
|
||||
|
||||
/**
|
||||
* Disable the radio.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully transitioned to Disabled.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError Disable(void);
|
||||
|
||||
/**
|
||||
* This method checks whether radio is enabled or not.
|
||||
*
|
||||
* @returns TRUE if the radio is enabled, FALSE otherwise.
|
||||
*
|
||||
*/
|
||||
bool IsEnabled(void) const { return mState != OT_RADIO_STATE_DISABLED; }
|
||||
|
||||
/**
|
||||
* This method updates the file descriptor sets with file descriptors used by the radio driver.
|
||||
*
|
||||
* @param[inout] aReadFdSet A reference to the read file descriptors.
|
||||
* @param[inout] aWriteFdSet A reference to the write file descriptors.
|
||||
* @param[inout] aMaxFd A reference to the max file descriptor.
|
||||
* @param[inout] aTimeout A reference to the timeout.
|
||||
*
|
||||
*/
|
||||
void UpdateFdSet(fd_set &aReadFdSet, fd_set &aWriteFdSet, int &aMaxFd, struct timeval &aTimeout);
|
||||
|
||||
/**
|
||||
* This method performs radio driver processing.
|
||||
*
|
||||
* @param[in] aReadFdSet A reference to the read file descriptors.
|
||||
* @param[in] aWriteFdSet A reference to the write file descriptors.
|
||||
*
|
||||
*/
|
||||
void Process(const fd_set &aReadFdSet, const fd_set &aWriteFdSet);
|
||||
|
||||
private:
|
||||
enum
|
||||
{
|
||||
kMaxSpinelFrame = 2048, ///< Max size in bytes for transfering spinel frames.
|
||||
kMaxWaitTime = 2000, ///< Max time to wait for response in milliseconds.
|
||||
};
|
||||
|
||||
void ReadAll(void);
|
||||
otError WriteAll(const uint8_t *aBuffer, uint16_t aLength);
|
||||
void ProcessFrameQueue(void);
|
||||
|
||||
/**
|
||||
* This method tries to retrieve a spinel property from OpenThread transceiver.
|
||||
*
|
||||
* @param[in] aKey Spinel property key.
|
||||
* @param[in] aFormat Spinel formatter to unpack property value.
|
||||
* @param[out] ... Variable arguments list.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully got the property.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError Get(spinel_prop_key_t aKey, const char *aFormat, ...);
|
||||
|
||||
/**
|
||||
* This method tries to update a spinel property of OpenThread transceiver.
|
||||
*
|
||||
* @param[in] aKey Spinel property key.
|
||||
* @param[in] aFormat Spinel formatter to pack property value.
|
||||
* @param[in] ... Variable arguments list.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully set the property.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError Set(spinel_prop_key_t aKey, const char *aFormat, ...);
|
||||
|
||||
/**
|
||||
* This method tries to insert a item into a spinel list property of OpenThread transceiver.
|
||||
*
|
||||
* @param[in] aKey Spinel property key.
|
||||
* @param[in] aFormat Spinel formatter to pack the item.
|
||||
* @param[in] ... Variable arguments list.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully insert item into the property.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError Insert(spinel_prop_key_t aKey, const char *aFormat, ...);
|
||||
|
||||
/**
|
||||
* This method tries to remove a item from a spinel list property of OpenThread transceiver.
|
||||
*
|
||||
* @param[in] aKey Spinel property key.
|
||||
* @param[in] aFormat Spinel formatter to pack the item.
|
||||
* @param[in] ... Variable arguments list.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully removed item from the property.
|
||||
* @retval OT_ERROR_BUSY Failed due to another operation is on going.
|
||||
* @retval OT_ERROR_RESPONSE_TIMEOUT Failed due to no response received from the transceiver.
|
||||
*
|
||||
*/
|
||||
otError Remove(spinel_prop_key_t aKey, const char *aFormat, ...);
|
||||
|
||||
spinel_tid_t GetNextTid(void);
|
||||
void FreeTid(spinel_tid_t tid) { mCmdTidsInUse &= ~(1 << tid); }
|
||||
|
||||
otError RequestV(bool aWait, uint32_t aCommand, spinel_prop_key_t aKey, const char *aFormat, va_list aArgs);
|
||||
otError Request(bool aWait, uint32_t aCommand, spinel_prop_key_t aKey, const char *aFormat, ...);
|
||||
otError WaitResponse(void);
|
||||
otError SendReset(void);
|
||||
otError SendCommand(uint32_t command,
|
||||
spinel_prop_key_t key,
|
||||
spinel_tid_t tid,
|
||||
const char * pack_format,
|
||||
va_list args);
|
||||
otError ParseRadioFrame(otRadioFrame &aFrame, const uint8_t *aBuffer, uint16_t aLength);
|
||||
|
||||
static void HandleHdlcError(void *aContext, otError aError, uint8_t *aBuffer, uint16_t aLength);
|
||||
static void HandleSpinelFrame(void *aContext, uint8_t *aBuffer, uint16_t aLength)
|
||||
{
|
||||
static_cast<RadioSpinel *>(aContext)->HandleSpinelFrame(aBuffer, aLength);
|
||||
}
|
||||
void HandleSpinelFrame(const uint8_t *aBuffer, uint16_t aLength);
|
||||
|
||||
void HandleNotification(const uint8_t *aBuffer, uint16_t aLength);
|
||||
void HandleValueIs(spinel_prop_key_t aKey, const uint8_t *aBuffer, uint16_t aLength);
|
||||
|
||||
void HandleResponse(const uint8_t *aBuffer, uint16_t aLength);
|
||||
void HandleTransmitDone(uint32_t aCommand, spinel_prop_key_t aKey, const uint8_t *aBuffer, uint16_t aLength);
|
||||
void HandleWaitingResponse(uint32_t aCommand, spinel_prop_key_t aKey, const uint8_t *aBuffer, uint16_t aLength);
|
||||
|
||||
void RadioReceive(void);
|
||||
void RadioTransmit(void);
|
||||
|
||||
otInstance *mInstance;
|
||||
|
||||
uint16_t mCmdTidsInUse; ///< Used transaction ids.
|
||||
spinel_tid_t mCmdNextTid; ///< Next available transaction id.
|
||||
spinel_tid_t mTxRadioTid; ///< The transaction id used to send a radio frame.
|
||||
spinel_tid_t mWaitingTid; ///< The transaction id of current transaction.
|
||||
spinel_prop_key_t mWaitingKey; ///< The property key of current transaction.
|
||||
const char * mPropertyFormat; ///< The spinel property format of current transaction.
|
||||
va_list mPropertyArgs; ///< The arguments pack or unpack spinel property of current transcation.
|
||||
uint32_t mExpectedCommand; ///< Expected response command of current transaction.
|
||||
otError mError; ///< The result of current transaction.
|
||||
|
||||
uint8_t mHdlcBuffer[kMaxSpinelFrame];
|
||||
Hdlc::Decoder mHdlcDecoder;
|
||||
Hdlc::Encoder mHdlcEncoder;
|
||||
FrameQueue mFrameQueue;
|
||||
|
||||
uint8_t mRxPsdu[OT_RADIO_FRAME_MAX_SIZE];
|
||||
uint8_t mTxPsdu[OT_RADIO_FRAME_MAX_SIZE];
|
||||
otRadioFrame mRxRadioFrame;
|
||||
otRadioFrame mTxRadioFrame;
|
||||
otRadioFrame *mTransmitFrame; ///< Points to the frame to send
|
||||
|
||||
otExtAddress mExtendedAddress;
|
||||
uint16_t mShortAddress;
|
||||
uint16_t mPanid;
|
||||
uint8_t mChannel;
|
||||
int8_t mRxSensitivity;
|
||||
uint8_t mTxState;
|
||||
otError mTxError;
|
||||
|
||||
int mSockFd;
|
||||
otRadioState mState;
|
||||
bool mAckWait;
|
||||
bool mPromiscuous;
|
||||
bool mIsReady;
|
||||
};
|
||||
|
||||
} // namespace ot
|
||||
|
||||
#endif // RADIO_SPINEL_HPP_
|
||||
@@ -0,0 +1,132 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 a pseudo-random number generator.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include "platform-posix.h"
|
||||
|
||||
#include <openthread/types.h>
|
||||
#include <openthread/platform/random.h>
|
||||
|
||||
#include "code_utils.h"
|
||||
|
||||
static uint32_t sState = 1;
|
||||
|
||||
void platformRandomInit(void)
|
||||
{
|
||||
#if __SANITIZE_ADDRESS__ == 0
|
||||
|
||||
otError error;
|
||||
|
||||
error = otPlatRandomGetTrue((uint8_t *)&sState, sizeof(sState));
|
||||
assert(error == OT_ERROR_NONE);
|
||||
|
||||
#else // __SANITIZE_ADDRESS__
|
||||
|
||||
// Multiplying NODE_ID assures that no two nodes gets the same seed within an hour.
|
||||
sState = (uint32_t)time(NULL) + (3600 * NODE_ID);
|
||||
|
||||
#endif // __SANITIZE_ADDRESS__
|
||||
}
|
||||
|
||||
uint32_t otPlatRandomGet(void)
|
||||
{
|
||||
uint32_t mlcg, p, q;
|
||||
uint64_t tmpstate;
|
||||
|
||||
tmpstate = (uint64_t)33614 * (uint64_t)sState;
|
||||
q = tmpstate & 0xffffffff;
|
||||
q = q >> 1;
|
||||
p = tmpstate >> 32;
|
||||
mlcg = p + q;
|
||||
|
||||
if (mlcg & 0x80000000)
|
||||
{
|
||||
mlcg &= 0x7fffffff;
|
||||
mlcg++;
|
||||
}
|
||||
|
||||
sState = mlcg;
|
||||
|
||||
return mlcg;
|
||||
}
|
||||
|
||||
otError otPlatRandomGetTrue(uint8_t *aOutput, uint16_t aOutputLength)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
|
||||
#if __SANITIZE_ADDRESS__ == 0
|
||||
|
||||
FILE * file = NULL;
|
||||
size_t readLength;
|
||||
|
||||
otEXPECT_ACTION(aOutput && aOutputLength, error = OT_ERROR_INVALID_ARGS);
|
||||
|
||||
file = fopen("/dev/urandom", "rb");
|
||||
otEXPECT_ACTION(file != NULL, error = OT_ERROR_FAILED);
|
||||
|
||||
readLength = fread(aOutput, 1, aOutputLength, file);
|
||||
otEXPECT_ACTION(readLength == aOutputLength, error = OT_ERROR_FAILED);
|
||||
|
||||
exit:
|
||||
|
||||
if (file != NULL)
|
||||
{
|
||||
fclose(file);
|
||||
}
|
||||
|
||||
#else // __SANITIZE_ADDRESS__
|
||||
|
||||
/*
|
||||
* THE IMPLEMENTATION BELOW IS NOT COMPLIANT WITH THE THREAD SPECIFICATION.
|
||||
*
|
||||
* Address Sanitizer triggers test failures when reading random
|
||||
* values from /dev/urandom. The pseudo-random number generator
|
||||
* implementation below is only used to enable continuous
|
||||
* integration checks with Address Sanitizer enabled.
|
||||
*/
|
||||
otEXPECT_ACTION(aOutput && aOutputLength, error = OT_ERROR_INVALID_ARGS);
|
||||
|
||||
for (uint16_t length = 0; length < aOutputLength; length++)
|
||||
{
|
||||
aOutput[length] = (uint8_t)otPlatRandomGet();
|
||||
}
|
||||
|
||||
exit:
|
||||
|
||||
#endif // __SANITIZE_ADDRESS__
|
||||
|
||||
return error;
|
||||
}
|
||||
@@ -0,0 +1,461 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 OpenThread platform abstraction for non-volatile storage of settings.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <stddef.h>
|
||||
#include <stdlib.h>
|
||||
#include "utils/wrap_string.h"
|
||||
|
||||
#include <openthread-core-config.h>
|
||||
|
||||
#include "openthread/platform/settings.h"
|
||||
#include "openthread/types.h"
|
||||
|
||||
#include <code_utils.h>
|
||||
|
||||
#include "flash.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
enum
|
||||
{
|
||||
kBlockAddBeginFlag = 0x1,
|
||||
kBlockAddCompleteFlag = 0x02,
|
||||
kBlockDeleteFlag = 0x04,
|
||||
kBlockIndex0Flag = 0x08,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
kSettingsFlagSize = 4,
|
||||
kSettingsBlockDataSize = 255,
|
||||
|
||||
kSettingsInSwap = 0xbe5cc5ef,
|
||||
kSettingsInUse = 0xbe5cc5ee,
|
||||
kSettingsNotUse = 0xbe5cc5ec,
|
||||
};
|
||||
|
||||
OT_TOOL_PACKED_BEGIN
|
||||
struct settingsBlock
|
||||
{
|
||||
uint16_t key;
|
||||
uint16_t flag;
|
||||
uint16_t length;
|
||||
uint16_t reserved;
|
||||
} OT_TOOL_PACKED_END;
|
||||
|
||||
/**
|
||||
* @def SETTINGS_CONFIG_BASE_ADDRESS
|
||||
*
|
||||
* The base address of settings.
|
||||
*
|
||||
*/
|
||||
#ifndef SETTINGS_CONFIG_BASE_ADDRESS
|
||||
#define SETTINGS_CONFIG_BASE_ADDRESS 0x39000
|
||||
#endif // SETTINGS_CONFIG_BASE_ADDRESS
|
||||
|
||||
/**
|
||||
* @def SETTINGS_CONFIG_PAGE_SIZE
|
||||
*
|
||||
* The page size of settings.
|
||||
*
|
||||
*/
|
||||
#ifndef SETTINGS_CONFIG_PAGE_SIZE
|
||||
#define SETTINGS_CONFIG_PAGE_SIZE 0x800
|
||||
#endif // SETTINGS_CONFIG_PAGE_SIZE
|
||||
|
||||
/**
|
||||
* @def SETTINGS_CONFIG_PAGE_NUM
|
||||
*
|
||||
* The page number of settings.
|
||||
*
|
||||
*/
|
||||
#ifndef SETTINGS_CONFIG_PAGE_NUM
|
||||
#define SETTINGS_CONFIG_PAGE_NUM 2
|
||||
#endif // SETTINGS_CONFIG_PAGE_NUM
|
||||
|
||||
static uint32_t sSettingsBaseAddress;
|
||||
static uint32_t sSettingsUsedSize;
|
||||
|
||||
static uint16_t getAlignLength(uint16_t length)
|
||||
{
|
||||
return (length + 3) & 0xfffc;
|
||||
}
|
||||
|
||||
static void setSettingsFlag(uint32_t aBase, uint32_t aFlag)
|
||||
{
|
||||
utilsFlashWrite(aBase, reinterpret_cast<uint8_t *>(&aFlag), sizeof(aFlag));
|
||||
}
|
||||
|
||||
static void initSettings(uint32_t aBase, uint32_t aFlag)
|
||||
{
|
||||
uint32_t address = aBase;
|
||||
uint32_t settingsSize = SETTINGS_CONFIG_PAGE_NUM > 1 ? SETTINGS_CONFIG_PAGE_SIZE * SETTINGS_CONFIG_PAGE_NUM / 2
|
||||
: SETTINGS_CONFIG_PAGE_SIZE;
|
||||
|
||||
while (address < (aBase + settingsSize))
|
||||
{
|
||||
utilsFlashErasePage(address);
|
||||
utilsFlashStatusWait(1000);
|
||||
address += SETTINGS_CONFIG_PAGE_SIZE;
|
||||
}
|
||||
|
||||
setSettingsFlag(aBase, aFlag);
|
||||
}
|
||||
|
||||
static uint32_t swapSettingsBlock(otInstance *aInstance)
|
||||
{
|
||||
uint32_t oldBase = sSettingsBaseAddress;
|
||||
uint32_t swapAddress = oldBase;
|
||||
uint32_t usedSize = sSettingsUsedSize;
|
||||
uint8_t pageNum = SETTINGS_CONFIG_PAGE_NUM;
|
||||
uint32_t settingsSize = pageNum > 1 ? SETTINGS_CONFIG_PAGE_SIZE * pageNum / 2 : SETTINGS_CONFIG_PAGE_SIZE;
|
||||
|
||||
(void)aInstance;
|
||||
|
||||
otEXPECT(pageNum > 1);
|
||||
|
||||
sSettingsBaseAddress =
|
||||
(swapAddress == SETTINGS_CONFIG_BASE_ADDRESS) ? (swapAddress + settingsSize) : SETTINGS_CONFIG_BASE_ADDRESS;
|
||||
|
||||
initSettings(sSettingsBaseAddress, static_cast<uint32_t>(kSettingsInSwap));
|
||||
sSettingsUsedSize = kSettingsFlagSize;
|
||||
swapAddress += kSettingsFlagSize;
|
||||
|
||||
while (swapAddress < (oldBase + usedSize))
|
||||
{
|
||||
OT_TOOL_PACKED_BEGIN
|
||||
struct addSettingsBlock
|
||||
{
|
||||
struct settingsBlock block;
|
||||
uint8_t data[kSettingsBlockDataSize];
|
||||
} OT_TOOL_PACKED_END addBlock;
|
||||
bool valid = true;
|
||||
|
||||
utilsFlashRead(swapAddress, reinterpret_cast<uint8_t *>(&addBlock.block), sizeof(struct settingsBlock));
|
||||
swapAddress += sizeof(struct settingsBlock);
|
||||
|
||||
if (!(addBlock.block.flag & kBlockAddCompleteFlag) && (addBlock.block.flag & kBlockDeleteFlag))
|
||||
{
|
||||
uint32_t address = swapAddress + getAlignLength(addBlock.block.length);
|
||||
|
||||
while (address < (oldBase + usedSize))
|
||||
{
|
||||
struct settingsBlock block;
|
||||
|
||||
utilsFlashRead(address, reinterpret_cast<uint8_t *>(&block), sizeof(block));
|
||||
|
||||
if (!(block.flag & kBlockAddCompleteFlag) && (block.flag & kBlockDeleteFlag) &&
|
||||
!(block.flag & kBlockIndex0Flag) && (block.key == addBlock.block.key))
|
||||
{
|
||||
valid = false;
|
||||
break;
|
||||
}
|
||||
|
||||
address += (getAlignLength(block.length) + sizeof(struct settingsBlock));
|
||||
}
|
||||
|
||||
if (valid)
|
||||
{
|
||||
utilsFlashRead(swapAddress, addBlock.data, getAlignLength(addBlock.block.length));
|
||||
utilsFlashWrite(sSettingsBaseAddress + sSettingsUsedSize, reinterpret_cast<uint8_t *>(&addBlock),
|
||||
getAlignLength(addBlock.block.length) + sizeof(struct settingsBlock));
|
||||
sSettingsUsedSize += (sizeof(struct settingsBlock) + getAlignLength(addBlock.block.length));
|
||||
}
|
||||
}
|
||||
else if (addBlock.block.flag == 0xff)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
swapAddress += getAlignLength(addBlock.block.length);
|
||||
}
|
||||
|
||||
setSettingsFlag(sSettingsBaseAddress, static_cast<uint32_t>(kSettingsInUse));
|
||||
setSettingsFlag(oldBase, static_cast<uint32_t>(kSettingsNotUse));
|
||||
|
||||
exit:
|
||||
return settingsSize - sSettingsUsedSize;
|
||||
}
|
||||
|
||||
static otError addSetting(otInstance * aInstance,
|
||||
uint16_t aKey,
|
||||
bool aIndex0,
|
||||
const uint8_t *aValue,
|
||||
uint16_t aValueLength)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
OT_TOOL_PACKED_BEGIN
|
||||
struct addSettingsBlock
|
||||
{
|
||||
struct settingsBlock block;
|
||||
uint8_t data[kSettingsBlockDataSize];
|
||||
} OT_TOOL_PACKED_END addBlock;
|
||||
uint32_t settingsSize = SETTINGS_CONFIG_PAGE_NUM > 1 ? SETTINGS_CONFIG_PAGE_SIZE * SETTINGS_CONFIG_PAGE_NUM / 2
|
||||
: SETTINGS_CONFIG_PAGE_SIZE;
|
||||
|
||||
addBlock.block.flag = 0xff;
|
||||
addBlock.block.key = aKey;
|
||||
|
||||
if (aIndex0)
|
||||
{
|
||||
addBlock.block.flag &= (~kBlockIndex0Flag);
|
||||
}
|
||||
|
||||
addBlock.block.flag &= (~kBlockAddBeginFlag);
|
||||
addBlock.block.length = aValueLength;
|
||||
|
||||
if ((sSettingsUsedSize + getAlignLength(addBlock.block.length) + sizeof(struct settingsBlock)) >= settingsSize)
|
||||
{
|
||||
otEXPECT_ACTION(swapSettingsBlock(aInstance) >=
|
||||
(getAlignLength(addBlock.block.length) + sizeof(struct settingsBlock)),
|
||||
error = OT_ERROR_NO_BUFS);
|
||||
}
|
||||
|
||||
utilsFlashWrite(sSettingsBaseAddress + sSettingsUsedSize, reinterpret_cast<uint8_t *>(&addBlock.block),
|
||||
sizeof(struct settingsBlock));
|
||||
|
||||
memset(addBlock.data, 0xff, kSettingsBlockDataSize);
|
||||
memcpy(addBlock.data, aValue, addBlock.block.length);
|
||||
|
||||
utilsFlashWrite(sSettingsBaseAddress + sSettingsUsedSize + sizeof(struct settingsBlock),
|
||||
reinterpret_cast<uint8_t *>(addBlock.data), getAlignLength(addBlock.block.length));
|
||||
|
||||
addBlock.block.flag &= (~kBlockAddCompleteFlag);
|
||||
utilsFlashWrite(sSettingsBaseAddress + sSettingsUsedSize, reinterpret_cast<uint8_t *>(&addBlock.block),
|
||||
sizeof(struct settingsBlock));
|
||||
sSettingsUsedSize += (sizeof(struct settingsBlock) + getAlignLength(addBlock.block.length));
|
||||
|
||||
exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
// settings API
|
||||
void otPlatSettingsInit(otInstance *aInstance)
|
||||
{
|
||||
uint8_t index;
|
||||
uint32_t settingsSize = SETTINGS_CONFIG_PAGE_NUM > 1 ? SETTINGS_CONFIG_PAGE_SIZE * SETTINGS_CONFIG_PAGE_NUM / 2
|
||||
: SETTINGS_CONFIG_PAGE_SIZE;
|
||||
|
||||
(void)aInstance;
|
||||
|
||||
sSettingsBaseAddress = SETTINGS_CONFIG_BASE_ADDRESS;
|
||||
|
||||
utilsFlashInit();
|
||||
|
||||
for (index = 0; index < 2; index++)
|
||||
{
|
||||
uint32_t blockFlag;
|
||||
|
||||
sSettingsBaseAddress += settingsSize * index;
|
||||
utilsFlashRead(sSettingsBaseAddress, reinterpret_cast<uint8_t *>(&blockFlag), sizeof(blockFlag));
|
||||
|
||||
if (blockFlag == kSettingsInUse)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (index == 2)
|
||||
{
|
||||
initSettings(sSettingsBaseAddress, static_cast<uint32_t>(kSettingsInUse));
|
||||
}
|
||||
|
||||
sSettingsUsedSize = kSettingsFlagSize;
|
||||
|
||||
while (sSettingsUsedSize < settingsSize)
|
||||
{
|
||||
struct settingsBlock block;
|
||||
|
||||
utilsFlashRead(sSettingsBaseAddress + sSettingsUsedSize, reinterpret_cast<uint8_t *>(&block), sizeof(block));
|
||||
|
||||
if (!(block.flag & kBlockAddBeginFlag))
|
||||
{
|
||||
sSettingsUsedSize += (getAlignLength(block.length) + sizeof(struct settingsBlock));
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
otError otPlatSettingsBeginChange(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
return OT_ERROR_NONE;
|
||||
}
|
||||
|
||||
otError otPlatSettingsCommitChange(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
return OT_ERROR_NONE;
|
||||
}
|
||||
|
||||
otError otPlatSettingsAbandonChange(otInstance *aInstance)
|
||||
{
|
||||
(void)aInstance;
|
||||
return OT_ERROR_NONE;
|
||||
}
|
||||
|
||||
otError otPlatSettingsGet(otInstance *aInstance, uint16_t aKey, int aIndex, uint8_t *aValue, uint16_t *aValueLength)
|
||||
{
|
||||
otError error = OT_ERROR_NOT_FOUND;
|
||||
uint32_t address = sSettingsBaseAddress + kSettingsFlagSize;
|
||||
uint16_t valueLength = 0;
|
||||
int index = 0;
|
||||
|
||||
(void)aInstance;
|
||||
|
||||
while (address < (sSettingsBaseAddress + sSettingsUsedSize))
|
||||
{
|
||||
struct settingsBlock block;
|
||||
|
||||
utilsFlashRead(address, reinterpret_cast<uint8_t *>(&block), sizeof(block));
|
||||
|
||||
if (block.key == aKey)
|
||||
{
|
||||
if (!(block.flag & kBlockIndex0Flag))
|
||||
{
|
||||
index = 0;
|
||||
}
|
||||
|
||||
if (!(block.flag & kBlockAddCompleteFlag) && (block.flag & kBlockDeleteFlag))
|
||||
{
|
||||
if (index == aIndex)
|
||||
{
|
||||
uint16_t readLength = block.length;
|
||||
|
||||
// only perform read if an input buffer was passed in
|
||||
if (aValue != NULL && aValueLength != NULL)
|
||||
{
|
||||
// adjust read length if input buffer length is smaller
|
||||
if (readLength > *aValueLength)
|
||||
{
|
||||
readLength = *aValueLength;
|
||||
}
|
||||
|
||||
utilsFlashRead(address + sizeof(struct settingsBlock), aValue, readLength);
|
||||
}
|
||||
|
||||
valueLength = block.length;
|
||||
error = OT_ERROR_NONE;
|
||||
}
|
||||
|
||||
index++;
|
||||
}
|
||||
}
|
||||
|
||||
address += (getAlignLength(block.length) + sizeof(struct settingsBlock));
|
||||
}
|
||||
|
||||
if (aValueLength != NULL)
|
||||
{
|
||||
*aValueLength = valueLength;
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
otError otPlatSettingsSet(otInstance *aInstance, uint16_t aKey, const uint8_t *aValue, uint16_t aValueLength)
|
||||
{
|
||||
return addSetting(aInstance, aKey, true, aValue, aValueLength);
|
||||
}
|
||||
|
||||
otError otPlatSettingsAdd(otInstance *aInstance, uint16_t aKey, const uint8_t *aValue, uint16_t aValueLength)
|
||||
{
|
||||
uint16_t length;
|
||||
bool index0;
|
||||
|
||||
index0 = (otPlatSettingsGet(aInstance, aKey, 0, NULL, &length) == OT_ERROR_NOT_FOUND ? true : false);
|
||||
return addSetting(aInstance, aKey, index0, aValue, aValueLength);
|
||||
}
|
||||
|
||||
otError otPlatSettingsDelete(otInstance *aInstance, uint16_t aKey, int aIndex)
|
||||
{
|
||||
otError error = OT_ERROR_NOT_FOUND;
|
||||
uint32_t address = sSettingsBaseAddress + kSettingsFlagSize;
|
||||
int index = 0;
|
||||
|
||||
(void)aInstance;
|
||||
|
||||
while (address < (sSettingsBaseAddress + sSettingsUsedSize))
|
||||
{
|
||||
struct settingsBlock block;
|
||||
|
||||
utilsFlashRead(address, reinterpret_cast<uint8_t *>(&block), sizeof(block));
|
||||
|
||||
if (block.key == aKey)
|
||||
{
|
||||
if (!(block.flag & kBlockIndex0Flag))
|
||||
{
|
||||
index = 0;
|
||||
}
|
||||
|
||||
if (!(block.flag & kBlockAddCompleteFlag) && (block.flag & kBlockDeleteFlag))
|
||||
{
|
||||
if (aIndex == index || aIndex == -1)
|
||||
{
|
||||
error = OT_ERROR_NONE;
|
||||
block.flag &= (~kBlockDeleteFlag);
|
||||
utilsFlashWrite(address, reinterpret_cast<uint8_t *>(&block), sizeof(block));
|
||||
}
|
||||
|
||||
if (index == 1 && aIndex == 0)
|
||||
{
|
||||
block.flag &= (~kBlockIndex0Flag);
|
||||
utilsFlashWrite(address, reinterpret_cast<uint8_t *>(&block), sizeof(block));
|
||||
}
|
||||
|
||||
index++;
|
||||
}
|
||||
}
|
||||
|
||||
address += (getAlignLength(block.length) + sizeof(struct settingsBlock));
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
void otPlatSettingsWipe(otInstance *aInstance)
|
||||
{
|
||||
initSettings(sSettingsBaseAddress, static_cast<uint32_t>(kSettingsInUse));
|
||||
otPlatSettingsInit(aInstance);
|
||||
}
|
||||
|
||||
#ifdef __cplusplus
|
||||
};
|
||||
#endif
|
||||
@@ -0,0 +1,93 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 spi stubs.
|
||||
*
|
||||
*/
|
||||
|
||||
#include "platform-posix.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <openthread/config.h>
|
||||
#include <openthread/platform/spi-slave.h>
|
||||
#include <openthread/platform/uart.h>
|
||||
|
||||
#if OPENTHREAD_ENABLE_NCP_SPI
|
||||
|
||||
// Spi-slave stubs
|
||||
|
||||
otError otPlatSpiSlaveEnable(otPlatSpiSlaveTransactionCompleteCallback aCompleteCallback,
|
||||
otPlatSpiSlaveTransactionProcessCallback aProcessCallback,
|
||||
void * aContext)
|
||||
{
|
||||
(void)aCompleteCallback;
|
||||
(void)aProcessCallback;
|
||||
(void)aContext;
|
||||
|
||||
fprintf(stderr, "\nNo SPI support for posix platform.");
|
||||
exit(0);
|
||||
|
||||
return OT_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
void otPlatSpiSlaveDisable(void)
|
||||
{
|
||||
}
|
||||
|
||||
otError otPlatSpiSlavePrepareTransaction(uint8_t *aOutputBuf,
|
||||
uint16_t aOutputBufLen,
|
||||
uint8_t *aInputBuf,
|
||||
uint16_t aInputBufLen,
|
||||
bool aRequestTransactionFlag)
|
||||
{
|
||||
(void)aOutputBuf;
|
||||
(void)aOutputBufLen;
|
||||
(void)aInputBuf;
|
||||
(void)aInputBufLen;
|
||||
(void)aRequestTransactionFlag;
|
||||
|
||||
return OT_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
// Uart
|
||||
|
||||
void otPlatUartSendDone(void)
|
||||
{
|
||||
}
|
||||
|
||||
void otPlatUartReceived(const uint8_t *aBuf, uint16_t aBufLength)
|
||||
{
|
||||
(void)aBuf;
|
||||
(void)aBufLength;
|
||||
}
|
||||
|
||||
#endif // OPENTHREAD_ENABLE_NCP_SPI
|
||||
Symlink
+1
@@ -0,0 +1 @@
|
||||
../../ncp/spinel.c
|
||||
@@ -0,0 +1,314 @@
|
||||
/*
|
||||
* Copyright (c) 2016, The OpenThread Authors.
|
||||
* 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 "platform-posix.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <signal.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/prctl.h>
|
||||
#include <termios.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <openthread/platform/debug_uart.h>
|
||||
#include <openthread/platform/uart.h>
|
||||
|
||||
#include "code_utils.h"
|
||||
|
||||
int posix_openpt(int oflag);
|
||||
int grantpt(int fildes);
|
||||
int unlockpt(int fd);
|
||||
char *ptsname(int fd);
|
||||
|
||||
static uint8_t s_receive_buffer[128];
|
||||
static const uint8_t *s_write_buffer;
|
||||
static uint16_t s_write_length;
|
||||
static int s_in_fd;
|
||||
static int s_out_fd;
|
||||
|
||||
static struct termios original_stdin_termios;
|
||||
static struct termios original_stdout_termios;
|
||||
|
||||
static void restore_stdin_termios(void)
|
||||
{
|
||||
tcsetattr(s_in_fd, TCSAFLUSH, &original_stdin_termios);
|
||||
}
|
||||
|
||||
static void restore_stdout_termios(void)
|
||||
{
|
||||
tcsetattr(s_out_fd, TCSAFLUSH, &original_stdout_termios);
|
||||
}
|
||||
|
||||
void platformUartRestore(void)
|
||||
{
|
||||
restore_stdin_termios();
|
||||
restore_stdout_termios();
|
||||
dup2(s_out_fd, STDOUT_FILENO);
|
||||
}
|
||||
|
||||
otError otPlatUartEnable(void)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
struct termios termios;
|
||||
|
||||
#ifdef OPENTHREAD_TARGET_LINUX
|
||||
// Ensure we terminate this process if the
|
||||
// parent process dies.
|
||||
prctl(PR_SET_PDEATHSIG, SIGHUP);
|
||||
#endif
|
||||
|
||||
s_in_fd = dup(STDIN_FILENO);
|
||||
s_out_fd = dup(STDOUT_FILENO);
|
||||
dup2(STDERR_FILENO, STDOUT_FILENO);
|
||||
|
||||
// We need this signal to make sure that this
|
||||
// process terminates properly.
|
||||
signal(SIGPIPE, SIG_DFL);
|
||||
|
||||
if (isatty(s_in_fd))
|
||||
{
|
||||
tcgetattr(s_in_fd, &original_stdin_termios);
|
||||
atexit(&restore_stdin_termios);
|
||||
}
|
||||
|
||||
if (isatty(s_out_fd))
|
||||
{
|
||||
tcgetattr(s_out_fd, &original_stdout_termios);
|
||||
atexit(&restore_stdout_termios);
|
||||
}
|
||||
|
||||
if (isatty(s_in_fd))
|
||||
{
|
||||
// get current configuration
|
||||
otEXPECT_ACTION(tcgetattr(s_in_fd, &termios) == 0, perror("tcgetattr"); error = OT_ERROR_GENERIC);
|
||||
|
||||
// Set up the termios settings for raw mode. This turns
|
||||
// off input/output processing, line processing, and character processing.
|
||||
cfmakeraw(&termios);
|
||||
|
||||
// Set up our cflags for local use. Turn on hangup-on-close.
|
||||
termios.c_cflag |= HUPCL | CREAD | CLOCAL;
|
||||
|
||||
// "Minimum number of characters for noncanonical read"
|
||||
termios.c_cc[VMIN] = 1;
|
||||
|
||||
// "Timeout in deciseconds for noncanonical read"
|
||||
termios.c_cc[VTIME] = 0;
|
||||
|
||||
// configure baud rate
|
||||
otEXPECT_ACTION(cfsetispeed(&termios, B115200) == 0, perror("cfsetispeed"); error = OT_ERROR_GENERIC);
|
||||
|
||||
// set configuration
|
||||
otEXPECT_ACTION(tcsetattr(s_in_fd, TCSANOW, &termios) == 0, perror("tcsetattr"); error = OT_ERROR_GENERIC);
|
||||
}
|
||||
|
||||
if (isatty(s_out_fd))
|
||||
{
|
||||
// get current configuration
|
||||
otEXPECT_ACTION(tcgetattr(s_out_fd, &termios) == 0, perror("tcgetattr"); error = OT_ERROR_GENERIC);
|
||||
|
||||
// Set up the termios settings for raw mode. This turns
|
||||
// off input/output processing, line processing, and character processing.
|
||||
cfmakeraw(&termios);
|
||||
|
||||
// Absolutely obliterate all output processing.
|
||||
termios.c_oflag = 0;
|
||||
|
||||
// Set up our cflags for local use. Turn on hangup-on-close.
|
||||
termios.c_cflag |= HUPCL | CREAD | CLOCAL;
|
||||
|
||||
// configure baud rate
|
||||
otEXPECT_ACTION(cfsetospeed(&termios, B115200) == 0, perror("cfsetospeed"); error = OT_ERROR_GENERIC);
|
||||
|
||||
// set configuration
|
||||
otEXPECT_ACTION(tcsetattr(s_out_fd, TCSANOW, &termios) == 0, perror("tcsetattr"); error = OT_ERROR_GENERIC);
|
||||
}
|
||||
|
||||
return error;
|
||||
|
||||
exit:
|
||||
close(s_in_fd);
|
||||
close(s_out_fd);
|
||||
return error;
|
||||
}
|
||||
|
||||
otError otPlatUartDisable(void)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
|
||||
close(s_in_fd);
|
||||
close(s_out_fd);
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
otError otPlatUartSend(const uint8_t *aBuf, uint16_t aBufLength)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
|
||||
otEXPECT_ACTION(s_write_length == 0, error = OT_ERROR_BUSY);
|
||||
|
||||
s_write_buffer = aBuf;
|
||||
s_write_length = aBufLength;
|
||||
|
||||
exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
void platformUartUpdateFdSet(fd_set *aReadFdSet, fd_set *aWriteFdSet, fd_set *aErrorFdSet, int *aMaxFd)
|
||||
{
|
||||
if (aReadFdSet != NULL)
|
||||
{
|
||||
FD_SET(s_in_fd, aReadFdSet);
|
||||
|
||||
if (aErrorFdSet != NULL)
|
||||
{
|
||||
FD_SET(s_in_fd, aErrorFdSet);
|
||||
}
|
||||
|
||||
if (aMaxFd != NULL && *aMaxFd < s_in_fd)
|
||||
{
|
||||
*aMaxFd = s_in_fd;
|
||||
}
|
||||
}
|
||||
|
||||
if ((aWriteFdSet != NULL) && (s_write_length > 0))
|
||||
{
|
||||
FD_SET(s_out_fd, aWriteFdSet);
|
||||
|
||||
if (aErrorFdSet != NULL)
|
||||
{
|
||||
FD_SET(s_out_fd, aErrorFdSet);
|
||||
}
|
||||
|
||||
if (aMaxFd != NULL && *aMaxFd < s_out_fd)
|
||||
{
|
||||
*aMaxFd = s_out_fd;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void platformUartProcess(const fd_set *aReadFdSet, const fd_set *aWriteFdSet, const fd_set *aErrorFdSet)
|
||||
{
|
||||
ssize_t rval;
|
||||
errno = 0;
|
||||
|
||||
if (FD_ISSET(s_in_fd, aErrorFdSet))
|
||||
{
|
||||
perror("s_in_fd");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
if (FD_ISSET(s_out_fd, aErrorFdSet))
|
||||
{
|
||||
perror("s_out_fd");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
if (FD_ISSET(s_in_fd, aReadFdSet))
|
||||
{
|
||||
rval = read(s_in_fd, s_receive_buffer, sizeof(s_receive_buffer));
|
||||
|
||||
if (rval < 0)
|
||||
{
|
||||
perror("read");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
else if (rval > 0)
|
||||
{
|
||||
otPlatUartReceived(s_receive_buffer, (uint16_t)rval);
|
||||
}
|
||||
}
|
||||
|
||||
if ((s_write_length > 0) && (FD_ISSET(s_out_fd, aWriteFdSet)))
|
||||
{
|
||||
rval = write(s_out_fd, s_write_buffer, s_write_length);
|
||||
|
||||
if (rval <= 0)
|
||||
{
|
||||
perror("write");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
s_write_buffer += (uint16_t)rval;
|
||||
s_write_length -= (uint16_t)rval;
|
||||
|
||||
if (s_write_length == 0)
|
||||
{
|
||||
otPlatUartSendDone();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#if OPENTHREAD_CONFIG_ENABLE_DEBUG_UART && (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_DEBUG_UART)
|
||||
|
||||
static FILE *posix_logfile;
|
||||
|
||||
otError otPlatDebugUart_logfile(const char *filename)
|
||||
{
|
||||
posix_logfile = fopen(filename, "wt");
|
||||
|
||||
return posix_logfile ? OT_ERROR_NONE : OT_ERROR_FAILED;
|
||||
}
|
||||
|
||||
void otPlatDebugUart_putchar_raw(int c)
|
||||
{
|
||||
FILE *fp;
|
||||
|
||||
/* note: log file will have a mix of cr/lf and
|
||||
* in some/many cases duplicate cr because in
|
||||
* some cases the log function {ie: Mbed} already
|
||||
* includes the CR or LF... but other log functions
|
||||
* do not include cr/lf and expect it appened
|
||||
*/
|
||||
fp = posix_logfile;
|
||||
|
||||
if (fp != NULL)
|
||||
{
|
||||
/* log is lost ... until a file is setup */
|
||||
fputc(c, fp);
|
||||
/* we could "fflush" but will not */
|
||||
}
|
||||
}
|
||||
|
||||
int otPlatDebugUart_kbhit(void)
|
||||
{
|
||||
/* not supported */
|
||||
return 0;
|
||||
}
|
||||
|
||||
int otPlatDebugUart_getc(void)
|
||||
{
|
||||
/* not supported */
|
||||
return -1;
|
||||
}
|
||||
|
||||
#endif
|
||||
+1
-1
@@ -48,7 +48,7 @@ PRETTY_SUBDIRS = \
|
||||
unit \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_EXAMPLES_POSIX
|
||||
if OPENTHREAD_POSIX
|
||||
if OPENTHREAD_ENABLE_CLI
|
||||
SUBDIRS += \
|
||||
unit \
|
||||
|
||||
@@ -39,7 +39,7 @@ DIST_SUBDIRS = \
|
||||
SUBDIRS = \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_EXAMPLES_POSIX
|
||||
if OPENTHREAD_POSIX
|
||||
if OPENTHREAD_ENABLE_CLI
|
||||
SUBDIRS += \
|
||||
thread-cert \
|
||||
|
||||
@@ -59,13 +59,17 @@ class otCli:
|
||||
|
||||
def __init_sim(self, nodeid, mode):
|
||||
""" Initialize a simulation node. """
|
||||
if "OT_CLI_PATH" in os.environ.keys():
|
||||
if 'OT_CLI_PATH' in os.environ.keys():
|
||||
cmd = os.environ['OT_CLI_PATH']
|
||||
elif "top_builddir" in os.environ.keys():
|
||||
elif 'top_builddir' in os.environ.keys():
|
||||
srcdir = os.environ['top_builddir']
|
||||
cmd = '%s/examples/apps/cli/ot-cli-%s' % (srcdir, mode)
|
||||
else:
|
||||
cmd = './ot-cli-%s' % mode
|
||||
|
||||
if 'RADIO_DEVICE' in os.environ:
|
||||
cmd += ' %s' % os.environ['RADIO_DEVICE']
|
||||
|
||||
cmd += ' %d' % nodeid
|
||||
print ("%s" % cmd)
|
||||
|
||||
@@ -77,11 +81,18 @@ class otCli:
|
||||
|
||||
def __init_ncp_sim(self, nodeid, mode):
|
||||
""" Initialize an NCP simulation node. """
|
||||
if "top_builddir" in os.environ.keys():
|
||||
builddir = os.environ['top_builddir']
|
||||
cmd = 'spinel-cli.py -p %s/examples/apps/ncp/ot-ncp-%s -n' % (builddir, mode)
|
||||
if 'RADIO_DEVICE' in os.environ:
|
||||
args = ' %s' % os.environ['RADIO_DEVICE']
|
||||
else:
|
||||
cmd = './ot-ncp-%s' % mode
|
||||
args = ''
|
||||
|
||||
if 'OT_NCP_PATH' in os.environ.keys():
|
||||
cmd = 'spinel-cli.py -p "%s%s" -n' % (os.environ['OT_NCP_PATH'], args)
|
||||
elif "top_builddir" in os.environ.keys():
|
||||
builddir = os.environ['top_builddir']
|
||||
cmd = 'spinel-cli.py -p "%s/examples/apps/ncp/ot-ncp-%s%s" -n' % (builddir, mode, args)
|
||||
else:
|
||||
cmd = 'spinel-cli.py -p "./ot-ncp-%s%s" -n' % (mode, args)
|
||||
cmd += ' %d' % nodeid
|
||||
print ("%s" % cmd)
|
||||
|
||||
@@ -106,6 +117,7 @@ class otCli:
|
||||
def send_command(self, cmd):
|
||||
print("%d: %s" % (self.nodeid, cmd))
|
||||
self.pexpect.send(cmd + '\n')
|
||||
sys.stdout.flush()
|
||||
|
||||
if isinstance(self.simulator, simulator.VirtualTime):
|
||||
self.simulator.receive_events()
|
||||
|
||||
+28
-4
@@ -51,12 +51,24 @@ if OPENTHREAD_BUILD_TESTS
|
||||
|
||||
AM_CPPFLAGS = \
|
||||
-DOPENTHREAD_FTD=1 \
|
||||
-I$(top_srcdir)/examples/platforms \
|
||||
-I$(top_srcdir)/include \
|
||||
-I$(top_srcdir)/src \
|
||||
-I$(top_srcdir)/src/core \
|
||||
$(NULL)
|
||||
|
||||
if OPENTHREAD_EXAMPLES_POSIX
|
||||
AM_CPPFLAGS += \
|
||||
-I$(top_srcdir)/examples/platforms \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
if OPENTHREAD_ENABLE_POSIX_APP
|
||||
AM_CPPFLAGS += \
|
||||
-DOPENTHREAD_ENABLE_POSIX_APP=1 \
|
||||
-I$(top_srcdir)/src/posix/platform \
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
if OPENTHREAD_ENABLE_NCP
|
||||
|
||||
COMMON_LDADD = \
|
||||
@@ -80,6 +92,12 @@ COMMON_LDADD += \
|
||||
$(NULL)
|
||||
endif # OPENTHREAD_ENABLE_BUILTIN_MBEDTLS
|
||||
|
||||
if OPENTHREAD_ENABLE_POSIX_APP
|
||||
COMMON_LDADD += \
|
||||
-lutil
|
||||
$(NULL)
|
||||
endif
|
||||
|
||||
# Test applications that should be run when the 'check' target is run.
|
||||
|
||||
check_PROGRAMS = \
|
||||
@@ -210,10 +228,16 @@ test_toolchain_LDADD = $(COMMON_LDADD)
|
||||
test_toolchain_SOURCES = test_platform.cpp test_toolchain.cpp test_toolchain_c.c
|
||||
|
||||
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_LDADD = $(top_builddir)/src/diag/libopenthread-diag.a
|
||||
test_diag_SOURCES = test_diag.cpp
|
||||
if OPENTHREAD_ENABLE_POSIX_APP
|
||||
test_diag_LDADD += $(top_builddir)/src/posix/platform/libopenthread-posix.a \
|
||||
-lutil \
|
||||
$(NULL)
|
||||
endif
|
||||
if OPENTHREAD_EXAMPLES_POSIX
|
||||
test_diag_LDADD += $(top_builddir)/examples/platforms/posix/libopenthread-posix.a
|
||||
endif
|
||||
endif
|
||||
|
||||
PRETTY_FILES = \
|
||||
|
||||
@@ -29,6 +29,8 @@
|
||||
#include <openthread/diag.h>
|
||||
#include <openthread/platform/radio.h>
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "utils/wrap_string.h"
|
||||
|
||||
#include "platform.h"
|
||||
@@ -227,9 +229,12 @@ void TestDiag(void)
|
||||
}};
|
||||
|
||||
// initialize platform layer
|
||||
int argc = 2;
|
||||
char *argv[8] = {(char *)"test_diag", (char *)"1"};
|
||||
PlatformInit(argc, argv);
|
||||
#if OPENTHREAD_ENABLE_POSIX_APP
|
||||
char *argv[] = {(char *)"test_diag", getenv("RADIO_DEVICE"), (char *)"1"};
|
||||
#else
|
||||
char *argv[] = {(char *)"test_diag", (char *)"1"};
|
||||
#endif
|
||||
PlatformInit(sizeof(argv) / sizeof(char *), argv);
|
||||
|
||||
// initialize diagnostics module
|
||||
otDiagInit(NULL);
|
||||
|
||||
Reference in New Issue
Block a user