mirror of
https://github.com/gnss-sdr/gnss-sdr
synced 2025-03-05 19:18:16 +00:00
Merge branch 'next' of https://github.com/mmajoral/gnss-sdr into fpga_extended_coherent_integration
This commit is contained in:
commit
05d006d1f9
@ -32,7 +32,6 @@ Checks: '-*,
|
||||
performance-inefficient-algorithm,
|
||||
performance-move-const-arg,
|
||||
performance-type-promotion-in-math-fn,
|
||||
performance-unnecessary-copy-initialization,
|
||||
performance-unnecessary-value-param,
|
||||
readability-container-size-empty,
|
||||
readability-identifier-naming,
|
||||
|
360
CMakeLists.txt
360
CMakeLists.txt
@ -143,7 +143,7 @@ if(NOT ${THIS_IS_A_RELEASE})
|
||||
find_package(Git)
|
||||
set_package_properties(Git PROPERTIES
|
||||
URL "https://git-scm.com"
|
||||
DESCRIPTION "A free and open source distributed version control system"
|
||||
DESCRIPTION "A free and open source distributed version control system (found: ${GIT_VERSION_STRING})"
|
||||
PURPOSE "Manage version control, get MINOR_VERSION name for version number."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
@ -295,6 +295,12 @@ if(${CMAKE_SYSTEM_NAME} MATCHES "Darwin")
|
||||
set(OS_IS_MACOSX TRUE)
|
||||
execute_process(COMMAND uname -v OUTPUT_VARIABLE DARWIN_VERSION)
|
||||
string(REGEX MATCH "[0-9]+" DARWIN_VERSION ${DARWIN_VERSION})
|
||||
if(${DARWIN_VERSION} MATCHES "19")
|
||||
set(MACOS_CATALINA TRUE)
|
||||
set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LANGUAGE_STANDARD "c++14")
|
||||
set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LIBRARY "libc++")
|
||||
message(STATUS "Configuring GNSS-SDR v${VERSION} to be built on macOS Catalina 10.15")
|
||||
endif()
|
||||
if(${DARWIN_VERSION} MATCHES "18")
|
||||
set(MACOS_MOJAVE TRUE)
|
||||
set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LANGUAGE_STANDARD "c++14")
|
||||
@ -468,7 +474,7 @@ endif()
|
||||
|
||||
|
||||
################################################################################
|
||||
# Set C and C++ standard
|
||||
# Set minimal C and C++ standards
|
||||
################################################################################
|
||||
if(NOT (CMAKE_VERSION VERSION_LESS "3.1"))
|
||||
set(CMAKE_C_STANDARD 11)
|
||||
@ -484,7 +490,7 @@ else()
|
||||
endif()
|
||||
endif()
|
||||
if(CMAKE_CXX_COMPILER_ID MATCHES "Clang")
|
||||
if(OS_IS_MACOSX)
|
||||
if(CMAKE_CXX_COMPILER_ID STREQUAL "AppleClang")
|
||||
if(CLANG_VERSION VERSION_LESS "600")
|
||||
add_compile_options("$<$<STREQUAL:$<TARGET_PROPERTY:LINKER_LANGUAGE>,CXX>:-std=c++11>")
|
||||
else()
|
||||
@ -604,16 +610,31 @@ set(GR_REQUIRED_COMPONENTS RUNTIME PMT BLOCKS FFT FILTER ANALOG)
|
||||
find_package(UHD)
|
||||
set_package_properties(UHD PROPERTIES
|
||||
URL "https://www.ettus.com/sdr-software/detail/usrp-hardware-driver"
|
||||
DESCRIPTION "USRP Hardware Driver"
|
||||
PURPOSE "Used for communication with front-ends of the USRP family."
|
||||
TYPE OPTIONAL
|
||||
)
|
||||
if(ENABLE_UHD)
|
||||
if(NOT UHD_FOUND)
|
||||
set(ENABLE_UHD OFF)
|
||||
set_package_properties(UHD PROPERTIES
|
||||
DESCRIPTION "USRP Hardware Driver"
|
||||
)
|
||||
else()
|
||||
set(GR_REQUIRED_COMPONENTS ${GR_REQUIRED_COMPONENTS} UHD)
|
||||
if(UHD_VERSION)
|
||||
set_package_properties(UHD PROPERTIES
|
||||
DESCRIPTION "USRP Hardware Driver (found: v${UHD_VERSION})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(UHD PROPERTIES
|
||||
DESCRIPTION "USRP Hardware Driver"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
else()
|
||||
set_package_properties(UHD PROPERTIES
|
||||
DESCRIPTION "USRP Hardware Driver"
|
||||
)
|
||||
endif()
|
||||
|
||||
find_package(GNURADIO)
|
||||
@ -623,147 +644,37 @@ set_package_properties(GNURADIO PROPERTIES
|
||||
PURPOSE "Implements flowgraph scheduler, provides some processing blocks and classes to create new ones."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(GNURADIO_VERSION)
|
||||
if(GNURADIO_VERSION VERSION_LESS ${GNSSSDR_GNURADIO_MIN_VERSION})
|
||||
unset(GNURADIO_RUNTIME_FOUND)
|
||||
message(STATUS "The GNU Radio version installed in your system (v${GNURADIO_VERSION}) is too old.")
|
||||
endif()
|
||||
endif()
|
||||
if(NOT GNURADIO_RUNTIME_FOUND)
|
||||
message(STATUS "CMake cannot find GNU Radio >= ${GNSSSDR_GNURADIO_MIN_VERSION}")
|
||||
if(OS_IS_LINUX)
|
||||
message("Go to https://github.com/gnuradio/pybombs")
|
||||
message("and follow the instructions to install GNU Radio in your system.")
|
||||
endif()
|
||||
if(OS_IS_MACOSX)
|
||||
message("You can install it easily via Macports:")
|
||||
message(" sudo port install gnuradio ")
|
||||
message("Alternatively, you can use homebrew:")
|
||||
message(" brew install gnuradio")
|
||||
endif()
|
||||
message(FATAL_ERROR "GNU Radio v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr.")
|
||||
else()
|
||||
if(NOT TARGET Gnuradio::runtime)
|
||||
add_library(Gnuradio::runtime SHARED IMPORTED)
|
||||
list(GET GNURADIO_RUNTIME_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_RUNTIME_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::runtime PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_RUNTIME_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_RUNTIME_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_RUNTIME_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT GNURADIO_ANALOG_FOUND)
|
||||
message(FATAL_ERROR "*** The gnuradio-analog library v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr")
|
||||
else()
|
||||
if(NOT TARGET Gnuradio::analog)
|
||||
add_library(Gnuradio::analog SHARED IMPORTED)
|
||||
list(GET GNURADIO_ANALOG_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_ANALOG_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::analog PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_ANALOG_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_ANALOG_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_ANALOG_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT GNURADIO_BLOCKS_FOUND)
|
||||
message(FATAL_ERROR "*** The gnuradio-blocks library v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr")
|
||||
else()
|
||||
if(NOT TARGET Gnuradio::blocks)
|
||||
add_library(Gnuradio::blocks SHARED IMPORTED)
|
||||
list(GET GNURADIO_BLOCKS_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_BLOCKS_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::blocks PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_BLOCKS_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_BLOCKS_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_BLOCKS_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT GNURADIO_FILTER_FOUND)
|
||||
message(FATAL_ERROR "*** The gnuradio-filter library v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr")
|
||||
else()
|
||||
if(NOT TARGET Gnuradio::filter)
|
||||
add_library(Gnuradio::filter SHARED IMPORTED)
|
||||
list(GET GNURADIO_FILTER_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_FILTER_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::filter PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_FILTER_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_FILTER_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_FILTER_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT GNURADIO_FFT_FOUND)
|
||||
message(FATAL_ERROR "*** The gnuradio-fft library v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr")
|
||||
else()
|
||||
if(NOT TARGET Gnuradio::fft)
|
||||
add_library(Gnuradio::fft SHARED IMPORTED)
|
||||
list(GET GNURADIO_FFT_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_FFT_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::fft PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_FFT_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_FFT_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_FFT_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT GNURADIO_PMT_FOUND)
|
||||
message(FATAL_ERROR "*** The gnuradio-pmt library v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr")
|
||||
else()
|
||||
if(NOT TARGET Gnuradio::pmt)
|
||||
add_library(Gnuradio::pmt SHARED IMPORTED)
|
||||
list(GET GNURADIO_PMT_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_PMT_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::pmt PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_PMT_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_PMT_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_PMT_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(ENABLE_UHD AND UHD_FOUND AND GNURADIO_UHD_FOUND)
|
||||
if(NOT TARGET Gnuradio::uhd)
|
||||
add_library(Gnuradio::uhd SHARED IMPORTED)
|
||||
list(GET GNURADIO_UHD_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_UHD_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::uhd PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_UHD_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_UHD_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_UHD_LIBRARIES}"
|
||||
)
|
||||
endif()
|
||||
################################################################################
|
||||
# Log4cpp - http://log4cpp.sourceforge.net/
|
||||
################################################################################
|
||||
find_package(LOG4CPP)
|
||||
set_package_properties(LOG4CPP PROPERTIES
|
||||
URL "http://log4cpp.sourceforge.net/"
|
||||
DESCRIPTION "Library of C++ classes for flexible logging to files"
|
||||
PURPOSE "Required by GNU Radio."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(NOT LOG4CPP_FOUND)
|
||||
message(FATAL_ERROR "*** Log4cpp is required to build gnss-sdr")
|
||||
endif()
|
||||
|
||||
|
||||
|
||||
################################################################################
|
||||
# Dectect availability of std::filesystem
|
||||
# Detect availability of std::filesystem and set C++ standard accordingly
|
||||
################################################################################
|
||||
set(FILESYSTEM_FOUND FALSE)
|
||||
if(NOT (GNURADIO_VERSION VERSION_LESS 3.8))
|
||||
if(NOT (GNURADIO_VERSION VERSION_LESS 3.8) AND LOG4CPP_READY_FOR_CXX17)
|
||||
# Check if we have std::filesystem
|
||||
if(NOT (CMAKE_VERSION VERSION_LESS 3.8))
|
||||
if(POLICY CMP0057)
|
||||
cmake_policy(SET CMP0057 NEW)
|
||||
endif()
|
||||
if(NOT ENABLE_UNIT_TESTING_EXTRA) # Workaround for GPSTk
|
||||
find_package(FILESYSTEM)
|
||||
find_package(FILESYSTEM COMPONENTS Final Experimental)
|
||||
set_package_properties(FILESYSTEM PROPERTIES
|
||||
URL "https://en.cppreference.com/w/cpp/filesystem"
|
||||
DESCRIPTION "Provides facilities for performing operations on file systems and their components"
|
||||
@ -771,7 +682,11 @@ if(NOT (GNURADIO_VERSION VERSION_LESS 3.8))
|
||||
TYPE OPTIONAL
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
if(CMAKE_VERSION VERSION_LESS 3.12)
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
else()
|
||||
set(CMAKE_CXX_STANDARD 20)
|
||||
endif()
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
endif()
|
||||
endif()
|
||||
@ -802,14 +717,25 @@ if(NOT ${FILESYSTEM_FOUND})
|
||||
set(BOOST_COMPONENTS ${BOOST_COMPONENTS} filesystem)
|
||||
endif()
|
||||
find_package(Boost ${GNSSSDR_BOOST_MIN_VERSION} COMPONENTS ${BOOST_COMPONENTS} REQUIRED)
|
||||
|
||||
if(NOT Boost_FOUND)
|
||||
message(FATAL_ERROR "Fatal error: Boost (version >=${GNSSSDR_BOOST_MIN_VERSION}) required.")
|
||||
endif()
|
||||
|
||||
set_package_properties(Boost PROPERTIES
|
||||
URL "https://www.boost.org"
|
||||
DESCRIPTION "Portable C++ source libraries"
|
||||
PURPOSE "Used widely across the source code."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(NOT Boost_FOUND)
|
||||
message(FATAL_ERROR "Fatal error: Boost (version >=${GNSSSDR_BOOST_MIN_VERSION}) required.")
|
||||
|
||||
if(CMAKE_VERSION VERSION_GREATER 3.14)
|
||||
set_package_properties(Boost PROPERTIES
|
||||
DESCRIPTION "Portable C++ source libraries (found: ${Boost_VERSION_STRING})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(Boost PROPERTIES
|
||||
DESCRIPTION "Portable C++ source libraries (found: ${Boost_MAJOR_VERSION}.${Boost_MINOR_VERSION}.${Boost_SUBMINOR_VERSION})"
|
||||
)
|
||||
endif()
|
||||
|
||||
if(CMAKE_VERSION VERSION_LESS 3.5)
|
||||
@ -894,37 +820,19 @@ endif()
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
################################################################################
|
||||
# VOLK - Vector-Optimized Library of Kernels
|
||||
################################################################################
|
||||
find_package(VOLK)
|
||||
set_package_properties(VOLK PROPERTIES
|
||||
URL "http://libvolk.org"
|
||||
DESCRIPTION "Vector-Optimized Library of Kernels"
|
||||
PURPOSE "Provides an abstraction of optimized math routines targeting several SIMD processors."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(NOT VOLK_FOUND)
|
||||
message(FATAL_ERROR "*** VOLK is required to build gnss-sdr")
|
||||
endif()
|
||||
|
||||
|
||||
|
||||
################################################################################
|
||||
# Log4cpp - http://log4cpp.sourceforge.net/
|
||||
################################################################################
|
||||
find_package(LOG4CPP)
|
||||
set_package_properties(LOG4CPP PROPERTIES
|
||||
URL "http://log4cpp.sourceforge.net/"
|
||||
DESCRIPTION "Library of C++ classes for flexible logging to files"
|
||||
PURPOSE "Required by GNU Radio."
|
||||
set_package_properties(VOLK PROPERTIES
|
||||
URL "http://libvolk.org"
|
||||
DESCRIPTION "Vector-Optimized Library of Kernels (found: ${VOLK_VERSION})"
|
||||
PURPOSE "Provides an abstraction of optimized math routines targeting several SIMD processors."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(NOT LOG4CPP_FOUND)
|
||||
message(FATAL_ERROR "*** Log4cpp is required to build gnss-sdr")
|
||||
endif()
|
||||
|
||||
|
||||
|
||||
@ -982,26 +890,32 @@ if(NOT VOLKGNSSSDR_FOUND)
|
||||
message(FATAL_ERROR "six - python 2 and 3 compatibility library required to build VOLK_GNSSSDR")
|
||||
endif()
|
||||
|
||||
if(Python3_FOUND)
|
||||
set_package_properties(Python3 PROPERTIES
|
||||
URL "https://www.python.org/"
|
||||
DESCRIPTION "An interpreted, high-level, general-purpose programming language"
|
||||
DESCRIPTION "An interpreted, high-level, general-purpose programming language (found: ${Python3_VERSION})"
|
||||
PURPOSE "Required to build volk_gnsssdr."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
endif()
|
||||
|
||||
if(Python2_FOUND)
|
||||
set_package_properties(Python2 PROPERTIES
|
||||
URL "https://www.python.org/"
|
||||
DESCRIPTION "An interpreted, high-level, general-purpose programming language"
|
||||
DESCRIPTION "An interpreted, high-level, general-purpose programming language (found: ${Python2_VERSION})"
|
||||
PURPOSE "Required to build volk_gnsssdr."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
endif()
|
||||
|
||||
if(PYTHONINTERP_FOUND)
|
||||
set_package_properties(PythonInterp PROPERTIES
|
||||
URL "https://www.python.org/"
|
||||
DESCRIPTION "An interpreted, high-level, general-purpose programming language"
|
||||
DESCRIPTION "An interpreted, high-level, general-purpose programming language (found: ${PYTHON_VERSION_STRING})"
|
||||
PURPOSE "Required to build volk_gnsssdr."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
endif()
|
||||
|
||||
set(READ_ENVIRO "")
|
||||
if(ENABLE_PACKAGING)
|
||||
@ -1233,37 +1147,30 @@ if(NOT GLOG_FOUND OR ${LOCAL_GFLAGS})
|
||||
set(GFLAGS_LIBRARIES_TO_LINK ${GFlags_LIBS})
|
||||
set(GFLAGS_LIBRARY_DIR_TO_LINK ${GFlags_LIBRARY_DIRS})
|
||||
endif()
|
||||
|
||||
if(CMAKE_CXX_COMPILER_ID MATCHES "Clang")
|
||||
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/tmp/configure_with_gflags
|
||||
"#!/bin/sh
|
||||
export CPPFLAGS=-I${GFlags_INCLUDE_DIRS}
|
||||
export LDFLAGS=-L${GFLAGS_LIBRARY_DIR_TO_LINK}
|
||||
export LIBS=\"${GFLAGS_LIBRARIES_TO_LINK} -lc++\"
|
||||
export CXXFLAGS=\"-stdlib=libc++\"
|
||||
export CC=clang
|
||||
export CXX=clang++
|
||||
cd ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/glog/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/
|
||||
aclocal
|
||||
automake --add-missing
|
||||
autoreconf -vfi
|
||||
cd ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/glog/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/configure"
|
||||
)
|
||||
else()
|
||||
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/tmp/configure_with_gflags
|
||||
"#!/bin/sh
|
||||
export CPPFLAGS=-I${GFlags_INCLUDE_DIRS}
|
||||
export LDFLAGS=-L${GFLAGS_LIBRARY_DIR_TO_LINK}
|
||||
export LIBS=${GFLAGS_LIBRARIES_TO_LINK}
|
||||
cd ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/glog/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/
|
||||
aclocal
|
||||
automake --add-missing
|
||||
autoreconf -vfi
|
||||
cd ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/glog/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/configure"
|
||||
)
|
||||
if(OS_IS_MACOSX)
|
||||
set(GFLAGS_LIBRARIES_TO_LINK "${GFLAGS_LIBRARIES_TO_LINK} -lc++")
|
||||
set(GLOG_EXPORT_CXX_LIBRARIES "export CXXFLAGS=\"-stdlib=libc++\"")
|
||||
endif()
|
||||
if(CMAKE_CXX_COMPILER_ID MATCHES "Clang")
|
||||
set(GLOG_EXPORT_C_COMPILER "export CC=clang")
|
||||
set(GLOG_EXPORT_CXX_COMPILER "export CXX=clang++")
|
||||
endif()
|
||||
|
||||
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/tmp/configure_with_gflags
|
||||
"#!/bin/sh
|
||||
export CPPFLAGS=-I${GFlags_INCLUDE_DIRS}
|
||||
export LDFLAGS=-L${GFLAGS_LIBRARY_DIR_TO_LINK}
|
||||
export LIBS=\"${GFLAGS_LIBRARIES_TO_LINK}\"
|
||||
${GLOG_EXPORT_CXX_LIBRARIES}
|
||||
${GLOG_EXPORT_C_COMPILER}
|
||||
${GLOG_EXPORT_CXX_COMPILER}
|
||||
cd ${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/glog/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/
|
||||
aclocal
|
||||
automake --add-missing
|
||||
autoreconf -vfi
|
||||
cd ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/thirdparty/glog/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/configure"
|
||||
)
|
||||
|
||||
file(COPY ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}/tmp/configure_with_gflags
|
||||
DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/glog-${GNSSSDR_GLOG_LOCAL_VERSION}
|
||||
@ -1457,11 +1364,13 @@ endif()
|
||||
find_package(Armadillo)
|
||||
set_package_properties(Armadillo PROPERTIES
|
||||
URL "http://arma.sourceforge.net/"
|
||||
DESCRIPTION "C++ library for linear algebra and scientific computing"
|
||||
PURPOSE "Used for matrix computations."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(ARMADILLO_FOUND)
|
||||
set_package_properties(Armadillo PROPERTIES
|
||||
DESCRIPTION "C++ library for linear algebra and scientific computing (found: v${ARMADILLO_VERSION_STRING})"
|
||||
)
|
||||
if(${ARMADILLO_VERSION_STRING} VERSION_LESS ${GNSSSDR_ARMADILLO_MIN_VERSION})
|
||||
set(ARMADILLO_FOUND false)
|
||||
set(ENABLE_OWN_ARMADILLO true)
|
||||
@ -1556,6 +1465,7 @@ if(NOT ARMADILLO_FOUND OR ENABLE_OWN_ARMADILLO)
|
||||
INTERFACE_LINK_LIBRARIES "${binary_dir}/${CMAKE_FIND_LIBRARY_PREFIXES}armadillo${CMAKE_STATIC_LIBRARY_SUFFIX}"
|
||||
)
|
||||
set_package_properties(Armadillo PROPERTIES
|
||||
DESCRIPTION "C++ library for linear algebra and scientific computing"
|
||||
PURPOSE "Armadillo ${GNSSSDR_ARMADILLO_LOCAL_VERSION} will be downloaded and built when doing '${CMAKE_MAKE_PROGRAM_PRETTY_NAME}'."
|
||||
)
|
||||
endif()
|
||||
@ -1614,7 +1524,7 @@ if(NOT GNUTLS_OPENSSL_LIBRARY)
|
||||
find_package(OpenSSL)
|
||||
set_package_properties(OpenSSL PROPERTIES
|
||||
URL "https://www.openssl.org"
|
||||
DESCRIPTION "Cryptography and SSL/TLS Toolkit"
|
||||
DESCRIPTION "Cryptography and SSL/TLS Toolkit (found: v${OPENSSL_VERSION})"
|
||||
PURPOSE "Used for the SUPL protocol implementation."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
@ -1651,7 +1561,6 @@ endif()
|
||||
find_package(MATIO)
|
||||
set_package_properties(MATIO PROPERTIES
|
||||
URL "https://github.com/tbeu/matio"
|
||||
DESCRIPTION "MATLAB MAT File I/O Library"
|
||||
PURPOSE "Used to store processing block's results in MAT files readable from MATLAB/Octave."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
@ -1661,6 +1570,9 @@ if(NOT MATIO_FOUND OR MATIO_VERSION_STRING VERSION_LESS ${GNSSSDR_MATIO_MIN_VERS
|
||||
endif()
|
||||
message(STATUS " Matio v${GNSSSDR_MATIO_LOCAL_VERSION} will be downloaded and built automatically")
|
||||
message(STATUS " when doing '${CMAKE_MAKE_PROGRAM_PRETTY_NAME}'.")
|
||||
set_package_properties(MATIO PROPERTIES
|
||||
DESCRIPTION "MATLAB MAT File I/O Library"
|
||||
)
|
||||
find_package(ZLIB)
|
||||
set_package_properties(ZLIB PROPERTIES
|
||||
URL "https://www.zlib.net/"
|
||||
@ -1791,6 +1703,10 @@ if(NOT MATIO_FOUND OR MATIO_VERSION_STRING VERSION_LESS ${GNSSSDR_MATIO_MIN_VERS
|
||||
set_package_properties(MATIO PROPERTIES
|
||||
PURPOSE "Matio v${GNSSSDR_MATIO_LOCAL_VERSION} will be downloaded and built when doing '${CMAKE_MAKE_PROGRAM_PRETTY_NAME}'."
|
||||
)
|
||||
else()
|
||||
set_package_properties(MATIO PROPERTIES
|
||||
DESCRIPTION "MATLAB MAT File I/O Library (found: v${MATIO_VERSION_STRING})"
|
||||
)
|
||||
endif()
|
||||
|
||||
|
||||
@ -1801,11 +1717,13 @@ endif()
|
||||
find_package(PUGIXML)
|
||||
set_package_properties(PUGIXML PROPERTIES
|
||||
URL "https://pugixml.org/"
|
||||
DESCRIPTION "Light-weight, simple and fast XML parser for C++"
|
||||
PURPOSE "Used to handle Galileo almanac XML files published by the European GNSS Service Centre."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
if(NOT PUGIXML_FOUND)
|
||||
set_package_properties(PUGIXML PROPERTIES
|
||||
DESCRIPTION "Light-weight, simple and fast XML parser for C++"
|
||||
)
|
||||
message(STATUS " PugiXML v${GNSSSDR_PUGIXML_LOCAL_VERSION} will be downloaded and built when doing '${CMAKE_MAKE_PROGRAM_PRETTY_NAME}'.")
|
||||
set(PUGIXML_COMPILER -DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER} -DCMAKE_C_COMPILER=${CMAKE_C_COMPILER})
|
||||
set(TOOLCHAIN_ARG "")
|
||||
@ -1855,6 +1773,16 @@ if(NOT PUGIXML_FOUND)
|
||||
set_package_properties(PUGIXML PROPERTIES
|
||||
PURPOSE "PugiXML v${GNSSSDR_PUGIXML_LOCAL_VERSION} will be downloaded and built when doing '${CMAKE_MAKE_PROGRAM_PRETTY_NAME}'."
|
||||
)
|
||||
else()
|
||||
if(PUGIXML_VERSION)
|
||||
set_package_properties(PUGIXML PROPERTIES
|
||||
DESCRIPTION "Light-weight, simple and fast XML parser for C++ (found: ${PUGIXML_VERSION})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(PUGIXML PROPERTIES
|
||||
DESCRIPTION "Light-weight, simple and fast XML parser for C++"
|
||||
)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
|
||||
@ -1865,7 +1793,6 @@ endif()
|
||||
find_package(Protobuf)
|
||||
set_package_properties(Protobuf PROPERTIES
|
||||
URL "https://developers.google.com/protocol-buffers/"
|
||||
DESCRIPTION "Structured data serialization mechanism"
|
||||
PURPOSE "Used to serialize output data in a way that can be read by other applications."
|
||||
TYPE REQUIRED
|
||||
)
|
||||
@ -1918,6 +1845,17 @@ if(Protobuf_FOUND AND CMAKE_VERSION VERSION_LESS 3.9)
|
||||
set(Protobuf_VERSION "${_PROTOBUF_MAJOR_VERSION}.${_PROTOBUF_MINOR_VERSION}.${_PROTOBUF_SUBMINOR_VERSION}")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(Protobuf_FOUND)
|
||||
set_package_properties(Protobuf PROPERTIES
|
||||
DESCRIPTION "Structured data serialization mechanism (found: v${Protobuf_VERSION})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(Protobuf PROPERTIES
|
||||
DESCRIPTION "Structured data serialization mechanism"
|
||||
)
|
||||
endif()
|
||||
|
||||
if(Protobuf_FOUND AND CMAKE_CROSSCOMPILING)
|
||||
find_program(PROTOC_EXECUTABLE protoc)
|
||||
if(NOT PROTOC_EXECUTABLE)
|
||||
@ -1937,6 +1875,7 @@ if(Protobuf_FOUND AND CMAKE_CROSSCOMPILING)
|
||||
message(FATAL_ERROR "Please install the Protocol Buffers compiler v${Protobuf_VERSION} in the host machine")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if((NOT Protobuf_FOUND) OR (NOT Protobuf_PROTOC_EXECUTABLE) OR (${Protobuf_VERSION} VERSION_LESS ${GNSSSDR_PROTOBUF_MIN_VERSION}))
|
||||
unset(Protobuf_PROTOC_EXECUTABLE)
|
||||
if(CMAKE_CROSSCOMPILING)
|
||||
@ -2258,7 +2197,6 @@ endif()
|
||||
find_package(GROSMOSDR)
|
||||
set_package_properties(GROSMOSDR PROPERTIES
|
||||
URL "https://osmocom.org/projects/gr-osmosdr/wiki"
|
||||
DESCRIPTION "osmocom GNU Radio blocks"
|
||||
PURPOSE "Used for communication with OsmoSDR and other front-ends (HackRF, bladeRF, Realtek's RTL2832U-based dongles, etc.)."
|
||||
TYPE OPTIONAL
|
||||
)
|
||||
@ -2266,7 +2204,19 @@ if(ENABLE_OSMOSDR)
|
||||
if(GROSMOSDR_FOUND)
|
||||
message(STATUS "The driver for OsmoSDR and other front-ends (HackRF, bladeRF, Realtek's RTL2832U-based dongles, etc.) will be compiled.")
|
||||
message(STATUS " You can disable it with 'cmake -DENABLE_OSMOSDR=OFF ..'")
|
||||
if(GROSMOSDR_VERSION)
|
||||
set_package_properties(GROSMOSDR PROPERTIES
|
||||
DESCRIPTION "osmocom GNU Radio blocks (found: ${GROSMOSDR_VERSION})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(GROSMOSDR PROPERTIES
|
||||
DESCRIPTION "osmocom GNU Radio blocks"
|
||||
)
|
||||
endif()
|
||||
else()
|
||||
set_package_properties(GROSMOSDR PROPERTIES
|
||||
DESCRIPTION "osmocom GNU Radio blocks"
|
||||
)
|
||||
if(ENABLE_PACKAGING)
|
||||
message(WARNING "gr-osmosdr has not been found. Source blocks depending on it will NOT be built.")
|
||||
else()
|
||||
@ -2274,6 +2224,9 @@ if(ENABLE_OSMOSDR)
|
||||
endif()
|
||||
endif()
|
||||
else()
|
||||
set_package_properties(GROSMOSDR PROPERTIES
|
||||
DESCRIPTION "osmocom GNU Radio blocks"
|
||||
)
|
||||
message(STATUS "The (optional) driver for OsmoSDR and related front-ends is not enabled.")
|
||||
message(STATUS " Enable it with 'cmake -DENABLE_OSMOSDR=ON ..' to add support for OsmoSDR and other front-ends (HackRF, bladeRF, Realtek's RTL2832U-based USB dongles, etc.)")
|
||||
endif()
|
||||
@ -2287,10 +2240,19 @@ endif()
|
||||
find_package(GRIIO)
|
||||
set_package_properties(GRIIO PROPERTIES
|
||||
URL "https://github.com/analogdevicesinc/gr-iio"
|
||||
DESCRIPTION "IIO blocks for GNU Radio"
|
||||
PURPOSE "Used for communication with PlutoSDR and FMCOMMS devices."
|
||||
TYPE OPTIONAL
|
||||
)
|
||||
if(GRIIO_FOUND AND GRIIO_VERSION)
|
||||
set_package_properties(GRIIO PROPERTIES
|
||||
DESCRIPTION "IIO blocks for GNU Radio (found: v${GRIIO_VERSION})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(GRIIO PROPERTIES
|
||||
DESCRIPTION "IIO blocks for GNU Radio"
|
||||
)
|
||||
endif()
|
||||
|
||||
|
||||
|
||||
#####################################################################
|
||||
@ -2301,10 +2263,18 @@ set_package_properties(GRIIO PROPERTIES
|
||||
find_package(LIBIIO)
|
||||
set_package_properties(LIBIIO PROPERTIES
|
||||
URL "https://github.com/analogdevicesinc/libiio"
|
||||
DESCRIPTION "A library for interfacing with Linux IIO devices"
|
||||
PURPOSE "Used for communication with the AD9361 chipset."
|
||||
TYPE OPTIONAL
|
||||
)
|
||||
if(LIBIIO_FOUND AND LIBIIO_VERSION)
|
||||
set_package_properties(LIBIIO PROPERTIES
|
||||
DESCRIPTION "A library for interfacing with Linux IIO devices (found: v${LIBIIO_VERSION})"
|
||||
)
|
||||
else()
|
||||
set_package_properties(LIBIIO PROPERTIES
|
||||
DESCRIPTION "A library for interfacing with Linux IIO devices"
|
||||
)
|
||||
endif()
|
||||
|
||||
|
||||
##############################################
|
||||
|
@ -45,12 +45,37 @@ find_library(GFORTRAN NAMES gfortran
|
||||
/usr/lib/gcc/i686-redhat-linux/4.8.2
|
||||
/usr/lib/gcc/x86_64-redhat-linux/7
|
||||
/usr/lib/gcc/i686-redhat-linux/7
|
||||
/usr/lib/gcc/x86_64-redhat-linux/8
|
||||
/usr/lib/gcc/i686-redhat-linux/8
|
||||
/usr/lib/gcc/x86_64-redhat-linux/9
|
||||
/usr/lib/gcc/i686-redhat-linux/9
|
||||
/usr/lib64/gcc/x86_64-redhat-linux/7
|
||||
/usr/lib64/gcc/x86_64-redhat-linux/8
|
||||
/usr/lib64/gcc/x86_64-redhat-linux/9
|
||||
/usr/lib/gcc/armv7hl-redhat-linux-gnueabi/7
|
||||
/usr/lib/gcc/aarch64-redhat-linux/7
|
||||
/usr/lib/gcc/i586-suse-linux/4.8 # OpenSUSE 13.1
|
||||
/usr/lib/gcc/i586-suse-linux/4.9
|
||||
/usr/lib/gcc/i586-suse-linux/7
|
||||
/usr/lib/gcc/i586-suse-linux/8
|
||||
/usr/lib/gcc/i586-suse-linux/9
|
||||
/usr/lib/gcc/x86_64-suse-linux/4.8
|
||||
/usr/lib/gcc/x86_64-suse-linux/4.9
|
||||
/usr/lib64/gcc/x86_64-suse-linux/7
|
||||
/usr/lib64/gcc/x86_64-suse-linux/8
|
||||
/usr/lib64/gcc/x86_64-suse-linux/9
|
||||
/usr/lib/gcc/armv7hl-suse-linux-gnueabi/7
|
||||
/usr/lib/gcc/armv7hl-suse-linux-gnueabi/8
|
||||
/usr/lib/gcc/armv7hl-suse-linux-gnueabi/9
|
||||
/usr/lib64/gcc/aarch64-suse-linux/7
|
||||
/usr/lib64/gcc/aarch64-suse-linux/8
|
||||
/usr/lib64/gcc/aarch64-suse-linux/9
|
||||
/usr/lib64/gcc/powerpc64-suse-linux/7
|
||||
/usr/lib64/gcc/powerpc64-suse-linux/8
|
||||
/usr/lib64/gcc/powerpc64-suse-linux/9
|
||||
/usr/lib64/gcc/powerpc64le-suse-linux/7
|
||||
/usr/lib64/gcc/powerpc64le-suse-linux/8
|
||||
/usr/lib64/gcc/powerpc64le-suse-linux/9
|
||||
/usr/lib/gcc/i486-linux-gnu # Debian 7
|
||||
/usr/lib/gcc/i486-linux-gnu/4.4
|
||||
/usr/lib/gcc/i486-linux-gnu/4.6
|
||||
@ -142,6 +167,24 @@ find_library(GFORTRAN NAMES gfortran
|
||||
/usr/lib/gcc/powerpc64le-linux-gnu/8
|
||||
/usr/lib/gcc/s390x-linux-gnu/8
|
||||
/usr/lib/gcc/alpha-linux-gnu/8
|
||||
/usr/lib/gcc/x86_64-linux-gnu/9
|
||||
/usr/lib/gcc/aarch64-linux-gnu/9
|
||||
/usr/lib/gcc/arm-linux-gnueabi/9
|
||||
/usr/lib/gcc/arm-linux-gnueabihf/9
|
||||
/usr/lib/gcc/i686-linux-gnu/9
|
||||
/usr/lib/gcc/powerpc64le-linux-gnu/9
|
||||
/usr/lib/gcc/powerpc64-linux-gnu/9/
|
||||
/usr/lib/gcc/s390x-linux-gnu/9
|
||||
/usr/lib/gcc/alpha-linux-gnu/9
|
||||
/usr/lib/gcc/hppa-linux-gnu/9
|
||||
/usr/lib/gcc/m68k-linux-gnu/9
|
||||
/usr/lib/gcc/mips-linux-gnu/9
|
||||
/usr/lib/gcc/mips64el-linux-gnuabi64/9
|
||||
/usr/lib/gcc/mipsel-linux-gnu/9
|
||||
/usr/lib/gcc/riscv64-linux-gnu/9
|
||||
/usr/lib/gcc/sh4-linux-gnu/9
|
||||
/usr/lib/gcc/sparc64-linux-gnu/9
|
||||
/usr/lib/gcc/x86_64-linux-gnux32/9
|
||||
${GFORTRAN_ROOT}/lib
|
||||
$ENV{GFORTRAN_ROOT}/lib
|
||||
)
|
||||
|
@ -143,6 +143,21 @@ function(GR_MODULE EXTVAR PCNAME INCFILE LIBFILE)
|
||||
set(GNURADIO_FOUND FALSE) # Trick for feature_summary
|
||||
endif()
|
||||
|
||||
# Create imported target
|
||||
string(TOLOWER ${EXTVAR} gnuradio_component)
|
||||
if(NOT TARGET Gnuradio::${gnuradio_component})
|
||||
add_library(Gnuradio::${gnuradio_component} SHARED IMPORTED)
|
||||
set(GNURADIO_LIBRARY ${GNURADIO_${EXTVAR}_LIBRARIES})
|
||||
list(GET GNURADIO_LIBRARY 0 FIRST_DIR)
|
||||
get_filename_component(GNURADIO_DIR ${FIRST_DIR} ABSOLUTE)
|
||||
set_target_properties(Gnuradio::${gnuradio_component} PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "CXX"
|
||||
IMPORTED_LOCATION "${GNURADIO_DIR}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${GNURADIO_${EXTVAR}_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${GNURADIO_LIBRARY}"
|
||||
)
|
||||
endif()
|
||||
|
||||
mark_as_advanced(GNURADIO_${EXTVAR}_LIBRARIES GNURADIO_${EXTVAR}_INCLUDE_DIRS)
|
||||
endfunction()
|
||||
|
||||
@ -218,3 +233,25 @@ if(NOT DEFINED GNURADIO_FOUND)
|
||||
set(GNURADIO_FOUND TRUE)
|
||||
endif()
|
||||
set(GNURADIO_VERSION ${PC_GNURADIO_RUNTIME_VERSION})
|
||||
|
||||
if(NOT GNSSSDR_GNURADIO_MIN_VERSION)
|
||||
set(GNSSSDR_GNURADIO_MIN_VERSION "3.7.3")
|
||||
endif()
|
||||
|
||||
if(GNURADIO_VERSION)
|
||||
if(GNURADIO_VERSION VERSION_LESS ${GNSSSDR_GNURADIO_MIN_VERSION})
|
||||
unset(GNURADIO_RUNTIME_FOUND)
|
||||
message(STATUS "The GNU Radio version installed in your system (v${GNURADIO_VERSION}) is too old.")
|
||||
if(OS_IS_LINUX)
|
||||
message("Go to https://github.com/gnuradio/pybombs")
|
||||
message("and follow the instructions to install GNU Radio in your system.")
|
||||
endif()
|
||||
if(OS_IS_MACOSX)
|
||||
message("You can install it easily via Macports:")
|
||||
message(" sudo port install gnuradio ")
|
||||
message("Alternatively, you can use homebrew:")
|
||||
message(" brew install gnuradio")
|
||||
endif()
|
||||
message(FATAL_ERROR "GNU Radio v${GNSSSDR_GNURADIO_MIN_VERSION} or later is required to build gnss-sdr.")
|
||||
endif()
|
||||
endif()
|
||||
|
@ -92,6 +92,10 @@ find_library(IIO_LIBRARIES
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(GRIIO DEFAULT_MSG IIO_LIBRARIES IIO_INCLUDE_DIRS)
|
||||
|
||||
if(PC_IIO_VERSION)
|
||||
set(GRIIO_VERSION ${PC_IIO_VERSION})
|
||||
endif()
|
||||
|
||||
if(GRIIO_FOUND AND NOT TARGET Gnuradio::iio)
|
||||
add_library(Gnuradio::iio SHARED IMPORTED)
|
||||
set_target_properties(Gnuradio::iio PROPERTIES
|
||||
|
@ -95,6 +95,10 @@ find_library(GROSMOSDR_LIBRARIES
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(GROSMOSDR DEFAULT_MSG GROSMOSDR_LIBRARIES GROSMOSDR_INCLUDE_DIR)
|
||||
|
||||
if(GROSMOSDR_PKG_VERSION)
|
||||
set(GROSMOSDR_VERSION ${GROSMOSDR_PKG_VERSION})
|
||||
endif()
|
||||
|
||||
if(GROSMOSDR_FOUND AND NOT TARGET Gnuradio::osmosdr)
|
||||
add_library(Gnuradio::osmosdr SHARED IMPORTED)
|
||||
set_target_properties(Gnuradio::osmosdr PROPERTIES
|
||||
|
@ -85,6 +85,10 @@ endif()
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(LIBIIO DEFAULT_MSG LIBIIO_LIBRARIES LIBIIO_INCLUDE_DIRS)
|
||||
|
||||
if(PC_LIBIIO_VERSION)
|
||||
set(LIBIIO_VERSION ${PC_LIBIIO_VERSION})
|
||||
endif()
|
||||
|
||||
if(LIBIIO_FOUND AND NOT TARGET Iio::iio)
|
||||
add_library(Iio::iio SHARED IMPORTED)
|
||||
set_target_properties(Iio::iio PROPERTIES
|
||||
|
@ -42,6 +42,7 @@ find_path(LIBOSMOSDR_INCLUDE_DIR NAMES osmosdr.h
|
||||
/usr/local/include
|
||||
${LIBOSMOSDR_ROOT}/include
|
||||
$ENV{LIBOSMOSDR_ROOT}/include
|
||||
${LIBOSMOSDR_PKG_INCLUDEDIR}
|
||||
)
|
||||
|
||||
find_library(LIBOSMOSDR_LIBRARIES NAMES osmosdr
|
||||
@ -77,6 +78,7 @@ find_library(LIBOSMOSDR_LIBRARIES NAMES osmosdr
|
||||
$ENV{LIBOSMOSDR_ROOT}/lib
|
||||
${LIBOSMOSDR_ROOT}/lib64
|
||||
$ENV{LIBOSMOSDR_ROOT}/lib64
|
||||
${LIBOSMOSDR_PKG_LIBDIR}
|
||||
)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
|
@ -39,6 +39,20 @@ find_path(LOG4CPP_INCLUDE_DIR log4cpp/Category.hh
|
||||
$ENV{LOG4CPP_ROOT}/include
|
||||
)
|
||||
|
||||
if(LOG4CPP_INCLUDE_DIR)
|
||||
file(STRINGS ${LOG4CPP_INCLUDE_DIR}/log4cpp/Priority.hh _log4cpp_Priority)
|
||||
set(_log4cpp_cxx17 TRUE)
|
||||
foreach(_loop_var IN LISTS _log4cpp_Priority)
|
||||
string(STRIP "${_loop_var}" _file_line)
|
||||
if("throw(std::invalid_argument);" STREQUAL "${_file_line}")
|
||||
set(_log4cpp_cxx17 FALSE)
|
||||
endif()
|
||||
endforeach()
|
||||
if(${_log4cpp_cxx17})
|
||||
set(LOG4CPP_READY_FOR_CXX17 TRUE)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
set(LOG4CPP_NAMES log4cpp)
|
||||
find_library(LOG4CPP_LIBRARY
|
||||
NAMES ${LOG4CPP_NAMES}
|
||||
@ -71,7 +85,6 @@ find_library(LOG4CPP_LIBRARY
|
||||
/usr/lib/alpha-linux-gnu
|
||||
/usr/lib64
|
||||
/usr/lib
|
||||
/usr/local/lib
|
||||
/opt/local/lib
|
||||
${LOG4CPP_ROOT}/lib
|
||||
$ENV{LOG4CPP_ROOT}/lib
|
||||
|
@ -27,6 +27,9 @@
|
||||
# Pugixml::pugixml
|
||||
#
|
||||
|
||||
include(FindPkgConfig)
|
||||
pkg_check_modules(PC_PUGIXML pugixml QUIET)
|
||||
|
||||
find_path(PUGIXML_INCLUDE_DIR
|
||||
NAMES pugixml.hpp
|
||||
PATHS ${PUGIXML_HOME}/include
|
||||
@ -38,6 +41,7 @@ find_path(PUGIXML_INCLUDE_DIR
|
||||
$ENV{PUGIXML_ROOT}/include
|
||||
${PUGIXML_ROOT}/include/pugixml-1.9
|
||||
$ENV{PUGIXML_ROOT}/include/pugixml-1.9
|
||||
${PC_PUGIXML_INCLUDEDIR}
|
||||
)
|
||||
|
||||
find_library(PUGIXML_LIBRARY
|
||||
@ -67,6 +71,7 @@ find_library(PUGIXML_LIBRARY
|
||||
$ENV{PUGIXML_ROOT}/lib/pugixml-1.9
|
||||
${PUGIXML_ROOT}/lib64/pugixml-1.9
|
||||
$ENV{PUGIXML_ROOT}/lib64/pugixml-1.9
|
||||
${PC_PUGIXML_LIBDIR}
|
||||
)
|
||||
|
||||
# Support the REQUIRED and QUIET arguments, and set PUGIXML_FOUND if found.
|
||||
@ -80,6 +85,9 @@ if(PUGIXML_FOUND)
|
||||
message(STATUS "PugiXML include = ${PUGIXML_INCLUDE_DIR}")
|
||||
message(STATUS "PugiXML library = ${PUGIXML_LIBRARY}")
|
||||
endif()
|
||||
if(PC_PUGIXML_VERSION)
|
||||
set(PUGIXML_VERSION ${PC_PUGIXML_VERSION})
|
||||
endif()
|
||||
else()
|
||||
message(STATUS "PugiXML not found.")
|
||||
endif()
|
||||
|
@ -77,6 +77,20 @@ find_library(UHD_LIBRARIES
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(UHD DEFAULT_MSG UHD_LIBRARIES UHD_INCLUDE_DIRS)
|
||||
|
||||
if(PC_UHD_VERSION)
|
||||
set(UHD_VERSION ${PC_UHD_VERSION})
|
||||
endif()
|
||||
if(NOT PC_UHD_VERSION)
|
||||
list(GET UHD_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(UHD_LIBRARIES_DIR ${FIRST_DIR} DIRECTORY)
|
||||
if(EXISTS ${UHD_LIBRARIES_DIR}/cmake/uhd/UHDConfigVersion.cmake)
|
||||
include(${UHD_LIBRARIES_DIR}/cmake/uhd/UHDConfigVersion.cmake)
|
||||
endif()
|
||||
if(PACKAGE_VERSION)
|
||||
set(UHD_VERSION ${PACKAGE_VERSION})
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(UHD_FOUND AND NOT TARGET Uhd::uhd)
|
||||
add_library(Uhd::uhd SHARED IMPORTED)
|
||||
set_target_properties(Uhd::uhd PROPERTIES
|
||||
|
@ -25,7 +25,7 @@
|
||||
########################################################################
|
||||
|
||||
include(FindPkgConfig)
|
||||
pkg_check_modules(PC_VOLK volk)
|
||||
pkg_check_modules(PC_VOLK volk QUIET)
|
||||
|
||||
find_path(VOLK_INCLUDE_DIRS
|
||||
NAMES volk/volk.h
|
||||
@ -78,6 +78,22 @@ find_library(VOLK_LIBRARIES
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
find_package_handle_standard_args(VOLK DEFAULT_MSG VOLK_LIBRARIES VOLK_INCLUDE_DIRS)
|
||||
|
||||
if(PC_VOLK_VERSION)
|
||||
set(VOLK_VERSION ${PC_VOLK_VERSION})
|
||||
endif()
|
||||
|
||||
if(NOT VOLK_VERSION)
|
||||
list(GET VOLK_LIBRARIES 0 FIRST_DIR)
|
||||
get_filename_component(VOLK_LIB_DIR ${FIRST_DIR} DIRECTORY)
|
||||
if(EXISTS ${VOLK_LIB_DIR}/cmake/volk/VolkConfigVersion.cmake)
|
||||
include(${VOLK_LIB_DIR}/cmake/volk/VolkConfigVersion.cmake)
|
||||
endif()
|
||||
if(PACKAGE_VERSION)
|
||||
set(VOLK_VERSION ${PACKAGE_VERSION})
|
||||
endif()
|
||||
endif()
|
||||
|
||||
mark_as_advanced(VOLK_LIBRARIES VOLK_INCLUDE_DIRS VOLK_VERSION)
|
||||
|
||||
if(VOLK_FOUND AND NOT TARGET Volk::volk)
|
||||
|
@ -16,7 +16,7 @@
|
||||
|
||||
- Improved preamble detection implementation in the decoding of navigation messages (acceleration by x1.6 on average per channel).
|
||||
- Shortened Acquisition to Tracking transition time.
|
||||
- Applied clang-tidy checks and fixes related to performance: performance-faster-string-find, performance-inefficient-algorithm, performance-move-const-arg, performance-type-promotion-in-math-fn, performance-unnecessary-copy-initialization, performance-unnecessary-value-param, readability-string-compare.
|
||||
- Applied clang-tidy checks and fixes related to performance: performance-faster-string-find, performance-inefficient-algorithm, performance-move-const-arg, performance-type-promotion-in-math-fn, performance-unnecessary-value-param, readability-string-compare.
|
||||
|
||||
|
||||
### Improvements in Flexibility:
|
||||
@ -50,7 +50,8 @@
|
||||
- Added interfaces for FPGA off-loading.
|
||||
- CMake scripts now follow a modern approach (targets and properties) but still work with 2.8.12.
|
||||
- Improvements for macOS users using Homebrew.
|
||||
- The volk_gnsssdr library can now be built without requiring Boost if the compiler supports C++17.
|
||||
- The volk_gnsssdr library can now be built without requiring Boost if the compiler supports C++17 or higher.
|
||||
- CMake scripts automatically select among C++11, C++14, C++17 or C++20 standards, the most recent as possible, depending on compiler and dependencies versions.
|
||||
|
||||
|
||||
### Improvements in Reliability
|
||||
@ -63,8 +64,9 @@
|
||||
- The receiver now admits FPGA off-loading, allowing for real time operation at high sampling rates and higher number of signals and channels.
|
||||
- Fixed program termination (avoiding hangs and segfaults in some platforms/configurations).
|
||||
- The Labsat_Signal_Source now terminates the receiver's execution when the end of file(s) is reached. It now accepts LabSat 2 filenames and series of LabSat 3 files.
|
||||
- CMake now generates a summary of enabled/disabled features. This info is also stored in a file called features.log in the building directory.
|
||||
- Added configuration parameters to set the annotation rate in KML, GPX, GeoJSON and NMEA outputs, set by default to 1 s.
|
||||
- New parameter PVT.show_local_time_zone displays time in the local time zone. Subject to the proper system configuration of the machine running the software receiver.
|
||||
- CMake now generates a summary of enabled/disabled features. This info is also stored in a file called features.log in the building directory.
|
||||
- Improved information provided to the user in case of failure.
|
||||
|
||||
|
||||
|
@ -138,6 +138,11 @@ Rtklib_Pvt::Rtklib_Pvt(ConfigurationInterface* configuration,
|
||||
pvt_output_parameters.rtcm_msg_rate_ms[k] = rtcm_MT1097_rate_ms;
|
||||
}
|
||||
|
||||
pvt_output_parameters.kml_rate_ms = bc::lcm(configuration->property(role + ".kml_rate_ms", pvt_output_parameters.kml_rate_ms), pvt_output_parameters.output_rate_ms);
|
||||
pvt_output_parameters.gpx_rate_ms = bc::lcm(configuration->property(role + ".gpx_rate_ms", pvt_output_parameters.gpx_rate_ms), pvt_output_parameters.output_rate_ms);
|
||||
pvt_output_parameters.geojson_rate_ms = bc::lcm(configuration->property(role + ".geojson_rate_ms", pvt_output_parameters.geojson_rate_ms), pvt_output_parameters.output_rate_ms);
|
||||
pvt_output_parameters.nmea_rate_ms = bc::lcm(configuration->property(role + ".nmea_rate_ms", pvt_output_parameters.nmea_rate_ms), pvt_output_parameters.output_rate_ms);
|
||||
|
||||
// Infer the type of receiver
|
||||
/*
|
||||
* TYPE | RECEIVER
|
||||
|
@ -30,6 +30,9 @@ add_library(pvt_gr_blocks ${PVT_GR_BLOCKS_SOURCES} ${PVT_GR_BLOCKS_HEADERS})
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(pvt_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(pvt_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(pvt_gr_blocks PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(pvt_gr_blocks PRIVATE Boost::filesystem Boost::system)
|
||||
|
@ -83,10 +83,15 @@
|
||||
#include <sys/msg.h> // for msgctl
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
namespace fs = std::filesystem;
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/path.hpp>
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
@ -173,6 +178,11 @@ rtklib_pvt_gs::rtklib_pvt_gs(uint32_t nchannels,
|
||||
std::string kml_dump_filename;
|
||||
kml_dump_filename = d_dump_filename;
|
||||
d_kml_output_enabled = conf_.kml_output_enabled;
|
||||
d_kml_rate_ms = conf_.kml_rate_ms;
|
||||
if (d_kml_rate_ms == 0)
|
||||
{
|
||||
d_kml_output_enabled = false;
|
||||
}
|
||||
if (d_kml_output_enabled)
|
||||
{
|
||||
d_kml_dump = std::make_shared<Kml_Printer>(conf_.kml_output_path);
|
||||
@ -187,6 +197,11 @@ rtklib_pvt_gs::rtklib_pvt_gs(uint32_t nchannels,
|
||||
std::string gpx_dump_filename;
|
||||
gpx_dump_filename = d_dump_filename;
|
||||
d_gpx_output_enabled = conf_.gpx_output_enabled;
|
||||
d_gpx_rate_ms = conf_.gpx_rate_ms;
|
||||
if (d_gpx_rate_ms == 0)
|
||||
{
|
||||
d_gpx_output_enabled = false;
|
||||
}
|
||||
if (d_gpx_output_enabled)
|
||||
{
|
||||
d_gpx_dump = std::make_shared<Gpx_Printer>(conf_.gpx_output_path);
|
||||
@ -201,6 +216,11 @@ rtklib_pvt_gs::rtklib_pvt_gs(uint32_t nchannels,
|
||||
std::string geojson_dump_filename;
|
||||
geojson_dump_filename = d_dump_filename;
|
||||
d_geojson_output_enabled = conf_.geojson_output_enabled;
|
||||
d_geojson_rate_ms = conf_.geojson_rate_ms;
|
||||
if (d_geojson_rate_ms == 0)
|
||||
{
|
||||
d_geojson_output_enabled = false;
|
||||
}
|
||||
if (d_geojson_output_enabled)
|
||||
{
|
||||
d_geojson_printer = std::make_shared<GeoJSON_Printer>(conf_.geojson_output_path);
|
||||
@ -213,6 +233,12 @@ rtklib_pvt_gs::rtklib_pvt_gs(uint32_t nchannels,
|
||||
|
||||
// initialize nmea_printer
|
||||
d_nmea_output_file_enabled = (conf_.nmea_output_file_enabled or conf_.flag_nmea_tty_port);
|
||||
d_nmea_rate_ms = conf_.nmea_rate_ms;
|
||||
if (d_nmea_rate_ms == 0)
|
||||
{
|
||||
d_nmea_output_file_enabled = false;
|
||||
}
|
||||
|
||||
if (d_nmea_output_file_enabled)
|
||||
{
|
||||
d_nmea_printer = std::make_shared<Nmea_Printer>(conf_.nmea_dump_filename, conf_.nmea_output_file_enabled, conf_.flag_nmea_tty_port, conf_.nmea_dump_devname, conf_.nmea_output_file_path);
|
||||
@ -1793,21 +1819,33 @@ int rtklib_pvt_gs::work(int noutput_items, gr_vector_const_void_star& input_item
|
||||
first_fix = false;
|
||||
}
|
||||
if (d_kml_output_enabled)
|
||||
{
|
||||
if (current_RX_time_ms % d_kml_rate_ms == 0)
|
||||
{
|
||||
d_kml_dump->print_position(d_pvt_solver, false);
|
||||
}
|
||||
}
|
||||
if (d_gpx_output_enabled)
|
||||
{
|
||||
if (current_RX_time_ms % d_gpx_rate_ms == 0)
|
||||
{
|
||||
d_gpx_dump->print_position(d_pvt_solver, false);
|
||||
}
|
||||
}
|
||||
if (d_geojson_output_enabled)
|
||||
{
|
||||
if (current_RX_time_ms % d_geojson_rate_ms == 0)
|
||||
{
|
||||
d_geojson_printer->print_position(d_pvt_solver, false);
|
||||
}
|
||||
}
|
||||
if (d_nmea_output_file_enabled)
|
||||
{
|
||||
if (current_RX_time_ms % d_nmea_rate_ms == 0)
|
||||
{
|
||||
d_nmea_printer->Print_Nmea_Line(d_pvt_solver, false);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* TYPE | RECEIVER
|
||||
|
@ -106,6 +106,11 @@ private:
|
||||
int32_t d_rtcm_MT1097_rate_ms; // Galileo MSM7. The type 7 Multiple Signal Message format for Europe’s Galileo system
|
||||
int32_t d_rtcm_MSM_rate_ms;
|
||||
|
||||
int32_t d_kml_rate_ms;
|
||||
int32_t d_gpx_rate_ms;
|
||||
int32_t d_geojson_rate_ms;
|
||||
int32_t d_nmea_rate_ms;
|
||||
|
||||
int32_t d_last_status_print_seg; // for status printer
|
||||
|
||||
uint32_t d_nchannels;
|
||||
|
@ -63,6 +63,9 @@ add_library(pvt_libs ${PVT_LIB_SOURCES} ${PVT_LIB_HEADERS})
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(pvt_libs PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(pvt_libs PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(pvt_libs PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(pvt_libs PRIVATE Boost::filesystem Boost::system)
|
||||
|
@ -33,15 +33,6 @@
|
||||
#include "geojson_printer.h"
|
||||
#include "pvt_solution.h"
|
||||
#include <boost/date_time/posix_time/posix_time.hpp>
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <glog/logging.h>
|
||||
#include <cstdio> // for remove
|
||||
#include <ctime> // for tm
|
||||
@ -51,9 +42,20 @@
|
||||
#include <sstream> // for stringstream
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -33,15 +33,6 @@
|
||||
#include "gpx_printer.h"
|
||||
#include "rtklib_solver.h"
|
||||
#include <boost/date_time/posix_time/posix_time.hpp>
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <glog/logging.h>
|
||||
#include <cstdio> // for remove
|
||||
#include <ctime> // for tm
|
||||
@ -51,9 +42,20 @@
|
||||
#include <sstream> // for stringstream
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -33,15 +33,6 @@
|
||||
#include "kml_printer.h"
|
||||
#include "rtklib_solver.h"
|
||||
#include <boost/date_time/posix_time/posix_time.hpp>
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <glog/logging.h>
|
||||
#include <cstdio> // for remove
|
||||
#include <cstdlib> // for mkstemp
|
||||
@ -55,9 +46,20 @@
|
||||
#include <sys/types.h> //for mode_t
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -36,15 +36,6 @@
|
||||
#include "nmea_printer.h"
|
||||
#include "rtklib_solution.h"
|
||||
#include "rtklib_solver.h"
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <glog/logging.h>
|
||||
#include <cstdint>
|
||||
#include <exception>
|
||||
@ -53,9 +44,20 @@
|
||||
#include <termios.h>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -35,6 +35,10 @@ Pvt_Conf::Pvt_Conf()
|
||||
type_of_receiver = 0U;
|
||||
output_rate_ms = 0;
|
||||
display_rate_ms = 0;
|
||||
kml_rate_ms = 1000;
|
||||
gpx_rate_ms = 1000;
|
||||
geojson_rate_ms = 1000;
|
||||
nmea_rate_ms = 1000;
|
||||
|
||||
rinex_version = 0;
|
||||
rinexobs_rate_ms = 0;
|
||||
|
@ -41,6 +41,10 @@ public:
|
||||
uint32_t type_of_receiver;
|
||||
int32_t output_rate_ms;
|
||||
int32_t display_rate_ms;
|
||||
int32_t kml_rate_ms;
|
||||
int32_t gpx_rate_ms;
|
||||
int32_t geojson_rate_ms;
|
||||
int32_t nmea_rate_ms;
|
||||
|
||||
int32_t rinex_version;
|
||||
int32_t rinexobs_rate_ms;
|
||||
|
@ -53,15 +53,6 @@
|
||||
#include <boost/date_time/gregorian/gregorian.hpp>
|
||||
#include <boost/date_time/local_time/local_time.hpp>
|
||||
#include <boost/date_time/time_zone_base.hpp>
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <glog/logging.h>
|
||||
#include <algorithm> // for min and max
|
||||
#include <cmath> // for floor
|
||||
@ -76,9 +67,20 @@
|
||||
#include <vector>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -39,16 +39,6 @@
|
||||
#include "gps_cnav_ephemeris.h"
|
||||
#include "gps_ephemeris.h"
|
||||
#include "rtcm.h"
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/date_time/posix_time/posix_time.hpp>
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_codes
|
||||
#endif
|
||||
#include <glog/logging.h>
|
||||
#include <cstdio> // for remove
|
||||
#include <ctime> // for tm
|
||||
@ -59,9 +49,20 @@
|
||||
#include <unistd.h> // for close, write
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -68,6 +68,9 @@ add_library(acquisition_gr_blocks ${ACQ_GR_BLOCKS_SOURCES} ${ACQ_GR_BLOCKS_HEADE
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(acquisition_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(acquisition_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(acquisition_gr_blocks PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(acquisition_gr_blocks PRIVATE Boost::filesystem)
|
||||
|
@ -40,7 +40,11 @@
|
||||
#include "gnss_sdr_create_directory.h"
|
||||
#include "gnss_synchro.h"
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
#else
|
||||
#include <filesystem>
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/path.hpp>
|
||||
#endif
|
||||
@ -58,7 +62,11 @@
|
||||
#include <map>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
namespace fs = boost::filesystem;
|
||||
#endif
|
||||
|
@ -35,7 +35,11 @@
|
||||
#include "gnss_sdr_create_directory.h"
|
||||
#include "gps_sdr_signal_processing.h"
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
#else
|
||||
#include <filesystem>
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/path.hpp>
|
||||
#endif
|
||||
@ -48,7 +52,11 @@
|
||||
#include <sstream>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
namespace fs = boost::filesystem;
|
||||
#endif
|
||||
|
@ -90,6 +90,9 @@ add_library(algorithms_libs ${GNSS_SPLIBS_SOURCES} ${GNSS_SPLIBS_HEADERS})
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(algorithms_libs PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(algorithms_libs PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(algorithms_libs PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(algorithms_libs PRIVATE Boost::filesystem Boost::system)
|
||||
@ -141,6 +144,9 @@ add_library(gnss_sdr_flags gnss_sdr_flags.cc gnss_sdr_flags.h)
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(gnss_sdr_flags PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
add_definitions(-DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(gnss_sdr_flags PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(gnss_sdr_flags PRIVATE Boost::filesystem)
|
||||
|
@ -29,22 +29,24 @@
|
||||
*/
|
||||
|
||||
#include "gnss_sdr_create_directory.h"
|
||||
#include <exception> // for exception
|
||||
#include <fstream> // for ofstream
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <exception> // for exception
|
||||
#include <fstream> // for ofstream
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
namespace errorlib = std;
|
||||
#else
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -30,18 +30,20 @@
|
||||
|
||||
|
||||
#include "gnss_sdr_flags.h"
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for exists
|
||||
#endif
|
||||
#include <cstdint>
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for exists
|
||||
namespace fs = boost::filesystem;
|
||||
#endif
|
||||
|
||||
@ -65,9 +67,12 @@ DEFINE_int32(cn0_samples, 20, "Number of correlator outputs used for CN0 estimat
|
||||
|
||||
DEFINE_int32(cn0_min, 25, "Minimum valid CN0 (in dB-Hz).");
|
||||
|
||||
DEFINE_int32(max_lock_fail, 50, "Maximum number of lock failures before dropping a satellite.");
|
||||
DEFINE_int32(max_carrier_lock_fail, 10000, "Maximum number of carrier lock failures before dropping a satellite.");
|
||||
|
||||
DEFINE_double(carrier_lock_th, 0.85, "Carrier lock threshold (in rad).");
|
||||
DEFINE_int32(max_lock_fail, 50, "Maximum number of code lock failures before dropping a satellite.");
|
||||
|
||||
//cos(2xError_angle)=0.7 -> Error_angle=22 deg
|
||||
DEFINE_double(carrier_lock_th, 0.7, "Carrier lock threshold (in rad).");
|
||||
|
||||
DEFINE_string(RINEX_version, "-", "If defined, specifies the RINEX version (2.11 or 3.02). Overrides the configuration file.");
|
||||
|
||||
|
@ -50,7 +50,8 @@ DECLARE_int32(doppler_step); //!< If defined, sets the frequency step in the se
|
||||
// Declare flags for tracking blocks
|
||||
DECLARE_int32(cn0_samples); //!< Number of correlator outputs used for CN0 estimation.
|
||||
DECLARE_int32(cn0_min); //!< Minimum valid CN0 (in dB-Hz).
|
||||
DECLARE_int32(max_lock_fail); //!< Maximum number of lock failures before dropping a satellite.
|
||||
DECLARE_int32(max_lock_fail); //!< Maximum number of code lock failures before dropping a satellite.
|
||||
DECLARE_int32(max_carrier_lock_fail); //!< Maximum number of carrier lock failures before dropping a satellite.
|
||||
DECLARE_double(carrier_lock_th); //!< Carrier lock threshold (in rad).
|
||||
DECLARE_double(dll_bw_hz); //!< Bandwidth of the DLL low pass filter, in Hz (overrides the configuration file).
|
||||
DECLARE_double(pll_bw_hz); //!< Bandwidth of the PLL low pass filter, in Hz (overrides the configuration file).
|
||||
|
@ -95,7 +95,11 @@ if((CMAKE_CXX_COMPILER_ID STREQUAL "GNU") AND NOT WIN32)
|
||||
set(CMAKE_CXX_STANDARD 14)
|
||||
else()
|
||||
if(${FILESYSTEM_FOUND})
|
||||
if(CMAKE_VERSION VERSION_LESS 3.12)
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
else()
|
||||
set(CMAKE_CXX_STANDARD 20)
|
||||
endif()
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
else()
|
||||
set(CMAKE_CXX_STANDARD 14)
|
||||
@ -134,7 +138,11 @@ if(CMAKE_CXX_COMPILER_ID MATCHES "Clang")
|
||||
set(CMAKE_CXX_STANDARD 14)
|
||||
else()
|
||||
if(${FILESYSTEM_FOUND})
|
||||
if(CMAKE_VERSION VERSION_LESS 3.12)
|
||||
set(CMAKE_CXX_STANDARD 17)
|
||||
else()
|
||||
set(CMAKE_CXX_STANDARD 20)
|
||||
endif()
|
||||
set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
else()
|
||||
set(CMAKE_CXX_STANDARD 14)
|
||||
|
@ -30,6 +30,9 @@ add_library(obs_gr_blocks ${OBS_GR_BLOCKS_SOURCES} ${OBS_GR_BLOCKS_HEADERS})
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(obs_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(obs_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(obs_gr_blocks PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(obs_gr_blocks PRIVATE Boost::filesystem)
|
||||
|
@ -46,13 +46,19 @@
|
||||
#include <utility> // for move
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/path.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
#endif
|
||||
|
||||
|
||||
hybrid_observables_gs_sptr hybrid_observables_gs_make(unsigned int nchannels_in, unsigned int nchannels_out, bool dump, bool dump_mat, std::string dump_filename)
|
||||
{
|
||||
return hybrid_observables_gs_sptr(new hybrid_observables_gs(nchannels_in, nchannels_out, dump, dump_mat, std::move(dump_filename)));
|
||||
|
@ -129,6 +129,7 @@ endif()
|
||||
|
||||
set(SIGNAL_SOURCE_ADAPTER_SOURCES
|
||||
file_signal_source.cc
|
||||
multichannel_file_signal_source.cc
|
||||
gen_signal_source.cc
|
||||
nsr_file_signal_source.cc
|
||||
spir_file_signal_source.cc
|
||||
@ -142,6 +143,7 @@ set(SIGNAL_SOURCE_ADAPTER_SOURCES
|
||||
|
||||
set(SIGNAL_SOURCE_ADAPTER_HEADERS
|
||||
file_signal_source.h
|
||||
multichannel_file_signal_source.h
|
||||
gen_signal_source.h
|
||||
nsr_file_signal_source.h
|
||||
spir_file_signal_source.h
|
||||
|
@ -0,0 +1,311 @@
|
||||
/*!
|
||||
* \file multichannel_file_signal_source.cc
|
||||
* \brief Implementation of a class that reads signals samples from files at
|
||||
* different frequency band and adapts it to a SignalSourceInterface
|
||||
* \author Javier Arribas, 2019 jarribas(at)cttc.es
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (C) 2010-2019 (see AUTHORS file for a list of contributors)
|
||||
*
|
||||
* GNSS-SDR is a software defined Global Navigation
|
||||
* Satellite Systems receiver
|
||||
*
|
||||
* This file is part of GNSS-SDR.
|
||||
*
|
||||
* GNSS-SDR is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNSS-SDR is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include "multichannel_file_signal_source.h"
|
||||
#include "configuration_interface.h"
|
||||
#include "gnss_sdr_flags.h"
|
||||
#include "gnss_sdr_valve.h"
|
||||
#include <glog/logging.h>
|
||||
#include <exception>
|
||||
#include <fstream>
|
||||
#include <iomanip>
|
||||
#include <iostream> // for std::cerr
|
||||
#include <utility>
|
||||
|
||||
|
||||
MultichannelFileSignalSource::MultichannelFileSignalSource(ConfigurationInterface* configuration,
|
||||
const std::string& role, unsigned int in_streams, unsigned int out_streams,
|
||||
boost::shared_ptr<gr::msg_queue> queue) : role_(role), in_streams_(in_streams), out_streams_(out_streams), queue_(std::move(queue))
|
||||
{
|
||||
std::string default_filename = "./example_capture.dat";
|
||||
std::string default_item_type = "short";
|
||||
std::string default_dump_filename = "./my_capture.dat";
|
||||
|
||||
double default_seconds_to_skip = 0.0;
|
||||
size_t header_size = 0;
|
||||
samples_ = configuration->property(role + ".samples", 0);
|
||||
sampling_frequency_ = configuration->property(role + ".sampling_frequency", 0);
|
||||
n_channels_ = configuration->property(role + ".total_channels", 1);
|
||||
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
filename_vec_.push_back(configuration->property(role + ".filename" + std::to_string(n), default_filename));
|
||||
}
|
||||
|
||||
item_type_ = configuration->property(role + ".item_type", default_item_type);
|
||||
repeat_ = configuration->property(role + ".repeat", false);
|
||||
enable_throttle_control_ = configuration->property(role + ".enable_throttle_control", false);
|
||||
|
||||
double seconds_to_skip = configuration->property(role + ".seconds_to_skip", default_seconds_to_skip);
|
||||
header_size = configuration->property(role + ".header_size", 0);
|
||||
int64_t samples_to_skip = 0;
|
||||
|
||||
bool is_complex = false;
|
||||
|
||||
if (item_type_ == "gr_complex")
|
||||
{
|
||||
item_size_ = sizeof(gr_complex);
|
||||
}
|
||||
else if (item_type_ == "float")
|
||||
{
|
||||
item_size_ = sizeof(float);
|
||||
}
|
||||
else if (item_type_ == "short")
|
||||
{
|
||||
item_size_ = sizeof(int16_t);
|
||||
}
|
||||
else if (item_type_ == "ishort")
|
||||
{
|
||||
item_size_ = sizeof(int16_t);
|
||||
is_complex = true;
|
||||
}
|
||||
else if (item_type_ == "byte")
|
||||
{
|
||||
item_size_ = sizeof(int8_t);
|
||||
}
|
||||
else if (item_type_ == "ibyte")
|
||||
{
|
||||
item_size_ = sizeof(int8_t);
|
||||
is_complex = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG(WARNING) << item_type_
|
||||
<< " unrecognized item type. Using gr_complex.";
|
||||
item_size_ = sizeof(gr_complex);
|
||||
}
|
||||
try
|
||||
{
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
file_source_vec_.push_back(gr::blocks::file_source::make(item_size_, filename_vec_.at(n).c_str(), repeat_));
|
||||
|
||||
if (seconds_to_skip > 0)
|
||||
{
|
||||
samples_to_skip = static_cast<int64_t>(seconds_to_skip * sampling_frequency_);
|
||||
|
||||
if (is_complex)
|
||||
{
|
||||
samples_to_skip *= 2;
|
||||
}
|
||||
}
|
||||
if (header_size > 0)
|
||||
{
|
||||
samples_to_skip += header_size;
|
||||
}
|
||||
|
||||
if (samples_to_skip > 0)
|
||||
{
|
||||
LOG(INFO) << "Skipping " << samples_to_skip << " samples of the input file #" << n;
|
||||
if (not file_source_vec_.back()->seek(samples_to_skip, SEEK_SET))
|
||||
{
|
||||
LOG(INFO) << "Error skipping bytes!";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
if (filename_vec_.at(0) == default_filename)
|
||||
{
|
||||
std::cerr
|
||||
<< "The configuration file has not been found."
|
||||
<< std::endl
|
||||
<< "Please create a configuration file based on the examples at the 'conf/' folder "
|
||||
<< std::endl
|
||||
<< "and then generate your own GNSS Software Defined Receiver by doing:"
|
||||
<< std::endl
|
||||
<< "$ gnss-sdr --config_file=/path/to/my_GNSS_SDR_configuration.conf"
|
||||
<< std::endl;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cerr
|
||||
<< "The receiver was configured to work with a file signal source "
|
||||
<< std::endl
|
||||
<< "but the specified file is unreachable by GNSS-SDR."
|
||||
<< std::endl
|
||||
<< "Please modify your configuration file"
|
||||
<< std::endl
|
||||
<< "and point SignalSource.filename to a valid raw data file. Then:"
|
||||
<< std::endl
|
||||
<< "$ gnss-sdr --config_file=/path/to/my_GNSS_SDR_configuration.conf"
|
||||
<< std::endl
|
||||
<< "Examples of configuration files available at:"
|
||||
<< std::endl
|
||||
<< GNSSSDR_INSTALL_DIR "/share/gnss-sdr/conf/"
|
||||
<< std::endl;
|
||||
}
|
||||
|
||||
LOG(INFO) << "file_signal_source: Unable to open the samples file "
|
||||
<< filename_vec_.at(0).c_str() << ", exiting the program.";
|
||||
throw(e);
|
||||
}
|
||||
|
||||
//todo from here.... add mux demux also
|
||||
if (samples_ == 0) // read all file
|
||||
{
|
||||
/*!
|
||||
* BUG workaround: The GNU Radio file source does not stop the receiver after reaching the End of File.
|
||||
* A possible solution is to compute the file length in samples using file size, excluding the last 100 milliseconds, and enable always the
|
||||
* valve block
|
||||
*/
|
||||
std::ifstream file(filename_vec_.at(0).c_str(), std::ios::in | std::ios::binary | std::ios::ate);
|
||||
std::ifstream::pos_type size;
|
||||
|
||||
if (file.is_open())
|
||||
{
|
||||
size = file.tellg();
|
||||
DLOG(INFO) << "Total samples in the file= " << floor(static_cast<double>(size) / static_cast<double>(item_size()));
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "file_signal_source: Unable to open the samples file " << filename_vec_.at(0).c_str() << std::endl;
|
||||
LOG(ERROR) << "file_signal_source: Unable to open the samples file " << filename_vec_.at(0).c_str();
|
||||
}
|
||||
std::streamsize ss = std::cout.precision();
|
||||
std::cout << std::setprecision(16);
|
||||
std::cout << "Processing file " << filename_vec_.at(0) << ", which contains " << static_cast<double>(size) << " [bytes]" << std::endl;
|
||||
std::cout.precision(ss);
|
||||
|
||||
if (size > 0)
|
||||
{
|
||||
int64_t bytes_to_skip = samples_to_skip * item_size_;
|
||||
int64_t bytes_to_process = static_cast<int64_t>(size) - bytes_to_skip;
|
||||
samples_ = floor(static_cast<double>(bytes_to_process) / static_cast<double>(item_size()) - ceil(0.002 * static_cast<double>(sampling_frequency_))); // process all the samples available in the file excluding at least the last 1 ms
|
||||
}
|
||||
}
|
||||
|
||||
CHECK(samples_ > 0) << "File does not contain enough samples to process.";
|
||||
double signal_duration_s;
|
||||
signal_duration_s = static_cast<double>(samples_) * (1 / static_cast<double>(sampling_frequency_));
|
||||
|
||||
if (is_complex)
|
||||
{
|
||||
signal_duration_s /= 2.0;
|
||||
}
|
||||
|
||||
DLOG(INFO) << "Total number samples to be processed= " << samples_ << " GNSS signal duration= " << signal_duration_s << " [s]";
|
||||
std::cout << "GNSS signal recorded time to be processed: " << signal_duration_s << " [s]" << std::endl;
|
||||
|
||||
valve_ = gnss_sdr_make_valve(item_size_, samples_, queue_);
|
||||
DLOG(INFO) << "valve(" << valve_->unique_id() << ")";
|
||||
|
||||
if (enable_throttle_control_)
|
||||
{
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
throttle_vec_.push_back(gr::blocks::throttle::make(item_size_, sampling_frequency_));
|
||||
}
|
||||
}
|
||||
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
LOG(INFO) << "Multichanne File source filename #" << n << filename_vec_.at(n);
|
||||
}
|
||||
|
||||
DLOG(INFO) << "Samples " << samples_;
|
||||
DLOG(INFO) << "Sampling frequency " << sampling_frequency_;
|
||||
DLOG(INFO) << "Item type " << item_type_;
|
||||
DLOG(INFO) << "Item size " << item_size_;
|
||||
DLOG(INFO) << "Repeat " << repeat_;
|
||||
|
||||
if (in_streams_ > 0)
|
||||
{
|
||||
LOG(ERROR) << "A signal source does not have an input stream";
|
||||
}
|
||||
if (out_streams_ > 1)
|
||||
{
|
||||
LOG(ERROR) << "This implementation only supports one output stream";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
MultichannelFileSignalSource::~MultichannelFileSignalSource() = default;
|
||||
|
||||
|
||||
void MultichannelFileSignalSource::connect(gr::top_block_sptr top_block)
|
||||
{
|
||||
if (enable_throttle_control_ == true)
|
||||
{
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
top_block->connect(file_source_vec_.at(n), 0, throttle_vec_.at(n), 0);
|
||||
DLOG(INFO) << "connected file_source #" << n << " to throttle";
|
||||
top_block->connect(throttle_vec_.at(n), 0, valve_, n);
|
||||
DLOG(INFO) << "connected throttle #" << n << " to valve_";
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
top_block->connect(file_source_vec_.at(n), 0, valve_, n);
|
||||
DLOG(INFO) << "connected file_source #" << n << " to valve_";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void MultichannelFileSignalSource::disconnect(gr::top_block_sptr top_block)
|
||||
{
|
||||
if (enable_throttle_control_ == true)
|
||||
{
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
top_block->disconnect(file_source_vec_.at(n), 0, throttle_vec_.at(n), 0);
|
||||
DLOG(INFO) << "disconnected file_source #" << n << " to throttle";
|
||||
top_block->disconnect(throttle_vec_.at(n), 0, valve_, n);
|
||||
DLOG(INFO) << "disconnected throttle #" << n << " to valve_";
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (unsigned int n = 0; n < n_channels_; n++)
|
||||
{
|
||||
top_block->disconnect(file_source_vec_.at(n), 0, valve_, n);
|
||||
DLOG(INFO) << "disconnected file_source #" << n << " to valve_";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
gr::basic_block_sptr MultichannelFileSignalSource::get_left_block()
|
||||
{
|
||||
LOG(WARNING) << "Left block of a signal source should not be retrieved";
|
||||
return gr::blocks::file_source::sptr();
|
||||
}
|
||||
|
||||
|
||||
gr::basic_block_sptr MultichannelFileSignalSource::get_right_block()
|
||||
{
|
||||
return valve_;
|
||||
}
|
@ -0,0 +1,131 @@
|
||||
/*!
|
||||
* \file multichannel_file_signal_source.h
|
||||
* \brief Implementation of a class that reads signals samples from files at
|
||||
* different frequency band and adapts it to a SignalSourceInterface
|
||||
* \author Javier Arribas, 2019 jarribas(at)cttc.es
|
||||
*
|
||||
* This class represents a file signal source. Internally it uses a GNU Radio's
|
||||
* gr_file_source as a connector to the data.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (C) 2010-2019 (see AUTHORS file for a list of contributors)
|
||||
*
|
||||
* GNSS-SDR is a software defined Global Navigation
|
||||
* Satellite Systems receiver
|
||||
*
|
||||
* This file is part of GNSS-SDR.
|
||||
*
|
||||
* GNSS-SDR is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNSS-SDR is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#ifndef GNSS_SDR_MULTICHANNEL_FILE_SIGNAL_SOURCE_H_
|
||||
#define GNSS_SDR_MULTICHANNEL_FILE_SIGNAL_SOURCE_H_
|
||||
|
||||
#include "gnss_block_interface.h"
|
||||
#include <gnuradio/blocks/file_sink.h>
|
||||
#include <gnuradio/blocks/file_source.h>
|
||||
#include <gnuradio/blocks/throttle.h>
|
||||
#include <gnuradio/hier_block2.h>
|
||||
#include <gnuradio/msg_queue.h>
|
||||
#include <cstdint>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
class ConfigurationInterface;
|
||||
|
||||
/*!
|
||||
* \brief Class that reads signals samples from files at different frequency bands
|
||||
* and adapts it to a SignalSourceInterface
|
||||
*/
|
||||
class MultichannelFileSignalSource : public GNSSBlockInterface
|
||||
{
|
||||
public:
|
||||
MultichannelFileSignalSource(ConfigurationInterface* configuration, const std::string& role,
|
||||
unsigned int in_streams, unsigned int out_streams,
|
||||
boost::shared_ptr<gr::msg_queue> queue);
|
||||
|
||||
virtual ~MultichannelFileSignalSource();
|
||||
|
||||
inline std::string role() override
|
||||
{
|
||||
return role_;
|
||||
}
|
||||
|
||||
/*!
|
||||
* \brief Returns "Multichannel_File_Signal_Source".
|
||||
*/
|
||||
inline std::string implementation() override
|
||||
{
|
||||
return "Multichannel_File_Signal_Source";
|
||||
}
|
||||
|
||||
inline size_t item_size() override
|
||||
{
|
||||
return item_size_;
|
||||
}
|
||||
|
||||
void connect(gr::top_block_sptr top_block) override;
|
||||
void disconnect(gr::top_block_sptr top_block) override;
|
||||
gr::basic_block_sptr get_left_block() override;
|
||||
gr::basic_block_sptr get_right_block() override;
|
||||
|
||||
inline std::string filename() const
|
||||
{
|
||||
return filename_vec_.at(0);
|
||||
}
|
||||
|
||||
inline std::string item_type() const
|
||||
{
|
||||
return item_type_;
|
||||
}
|
||||
|
||||
inline bool repeat() const
|
||||
{
|
||||
return repeat_;
|
||||
}
|
||||
|
||||
inline int64_t sampling_frequency() const
|
||||
{
|
||||
return sampling_frequency_;
|
||||
}
|
||||
|
||||
inline uint64_t samples() const
|
||||
{
|
||||
return samples_;
|
||||
}
|
||||
|
||||
private:
|
||||
uint64_t samples_;
|
||||
int64_t sampling_frequency_;
|
||||
uint32_t n_channels_;
|
||||
std::vector<std::string> filename_vec_;
|
||||
std::string item_type_;
|
||||
bool repeat_;
|
||||
std::string role_;
|
||||
uint32_t in_streams_;
|
||||
uint32_t out_streams_;
|
||||
std::vector<gr::blocks::file_source::sptr> file_source_vec_;
|
||||
boost::shared_ptr<gr::block> valve_;
|
||||
gr::blocks::file_sink::sptr sink_;
|
||||
std::vector<gr::blocks::throttle::sptr> throttle_vec_;
|
||||
boost::shared_ptr<gr::msg_queue> queue_;
|
||||
size_t item_size_;
|
||||
// Throttle control
|
||||
bool enable_throttle_control_;
|
||||
};
|
||||
|
||||
#endif /* GNSS_SDR_MULTICHANNEL_FILE_SIGNAL_SOURCE_H_ */
|
@ -44,8 +44,8 @@ Gnss_Sdr_Valve::Gnss_Sdr_Valve(size_t sizeof_stream_item,
|
||||
uint64_t nitems,
|
||||
gr::msg_queue::sptr queue,
|
||||
bool stop_flowgraph) : gr::sync_block("valve",
|
||||
gr::io_signature::make(1, 1, sizeof_stream_item),
|
||||
gr::io_signature::make(1, 1, sizeof_stream_item)),
|
||||
gr::io_signature::make(1, 20, sizeof_stream_item),
|
||||
gr::io_signature::make(1, 20, sizeof_stream_item)),
|
||||
d_nitems(nitems),
|
||||
d_ncopied_items(0),
|
||||
d_queue(std::move(queue)),
|
||||
@ -99,11 +99,17 @@ int Gnss_Sdr_Valve::work(int noutput_items,
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
memcpy(output_items[0], input_items[0], n * input_signature()->sizeof_stream_item(0));
|
||||
// multichannel support
|
||||
for (unsigned int ch = 0; ch < output_items.size(); ch++)
|
||||
{
|
||||
memcpy(output_items[ch], input_items[ch], n * input_signature()->sizeof_stream_item(ch));
|
||||
}
|
||||
d_ncopied_items += n;
|
||||
return n;
|
||||
}
|
||||
|
||||
memcpy(output_items[0], input_items[0], noutput_items * input_signature()->sizeof_stream_item(0));
|
||||
for (unsigned int ch = 0; ch < output_items.size(); ch++)
|
||||
{
|
||||
memcpy(output_items[ch], input_items[ch], noutput_items * input_signature()->sizeof_stream_item(ch));
|
||||
}
|
||||
return noutput_items;
|
||||
}
|
||||
|
@ -97,7 +97,7 @@ galileo_telemetry_decoder_gs::galileo_telemetry_decoder_gs(
|
||||
d_frame_length_symbols = GALILEO_INAV_PAGE_PART_SYMBOLS - GALILEO_INAV_PREAMBLE_LENGTH_BITS;
|
||||
CodeLength = GALILEO_INAV_PAGE_PART_SYMBOLS - GALILEO_INAV_PREAMBLE_LENGTH_BITS;
|
||||
DataLength = (CodeLength / nn) - mm;
|
||||
d_max_symbols_without_valid_frame = GALILEO_INAV_PAGE_PART_SYMBOLS * 30; //rise alarm 30 seconds without valid tlm
|
||||
d_max_symbols_without_valid_frame = GALILEO_INAV_PAGE_SYMBOLS * 30; //rise alarm 60 seconds without valid tlm
|
||||
|
||||
break;
|
||||
}
|
||||
@ -127,7 +127,7 @@ galileo_telemetry_decoder_gs::galileo_telemetry_decoder_gs(
|
||||
d_secondary_code_samples[i] = -1;
|
||||
}
|
||||
}
|
||||
d_max_symbols_without_valid_frame = GALILEO_FNAV_CODES_PER_SYMBOL * GALILEO_FNAV_SYMBOLS_PER_PAGE * 30; //rise alarm 30 seconds without valid tlm
|
||||
d_max_symbols_without_valid_frame = GALILEO_FNAV_CODES_PER_PAGE * 10; //rise alarm 100 seconds without valid tlm
|
||||
break;
|
||||
}
|
||||
default:
|
||||
@ -452,8 +452,10 @@ void galileo_telemetry_decoder_gs::set_satellite(const Gnss_Satellite &satellite
|
||||
|
||||
void galileo_telemetry_decoder_gs::reset()
|
||||
{
|
||||
gr::thread::scoped_lock lock(d_setlock);
|
||||
d_last_valid_preamble = d_sample_counter;
|
||||
d_sent_tlm_failed_msg = false;
|
||||
d_stat = 0;
|
||||
DLOG(INFO) << "Telemetry decoder reset for satellite " << d_satellite;
|
||||
}
|
||||
|
||||
@ -501,11 +503,12 @@ int galileo_telemetry_decoder_gs::general_work(int noutput_items __attribute__((
|
||||
d_flag_preamble = false;
|
||||
|
||||
// check if there is a problem with the telemetry of the current satellite
|
||||
if (d_stat < 1 and d_sent_tlm_failed_msg == false)
|
||||
if (d_sent_tlm_failed_msg == false)
|
||||
{
|
||||
if ((d_sample_counter - d_last_valid_preamble) > d_max_symbols_without_valid_frame)
|
||||
{
|
||||
int message = 1; //bad telemetry
|
||||
DLOG(INFO) << "sent msg sat " << this->d_satellite;
|
||||
this->message_port_pub(pmt::mp("telemetry_to_trk"), pmt::make_any(message));
|
||||
d_sent_tlm_failed_msg = true;
|
||||
}
|
||||
|
@ -430,7 +430,14 @@ int gps_l1_ca_telemetry_decoder_gs::general_work(int noutput_items __attribute__
|
||||
{
|
||||
DLOG(INFO) << "Preamble confirmation for SAT " << this->d_satellite;
|
||||
d_preamble_index = d_sample_counter; // record the preamble sample stamp
|
||||
if (corr_value < 0) flag_PLL_180_deg_phase_locked = true;
|
||||
if (corr_value < 0)
|
||||
{
|
||||
flag_PLL_180_deg_phase_locked = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
flag_PLL_180_deg_phase_locked = false;
|
||||
}
|
||||
d_stat = 2;
|
||||
}
|
||||
else
|
||||
|
@ -64,7 +64,7 @@ gps_l5_telemetry_decoder_gs::gps_l5_telemetry_decoder_gs(
|
||||
this->message_port_register_out(pmt::mp("telemetry_to_trk"));
|
||||
d_last_valid_preamble = 0;
|
||||
d_sent_tlm_failed_msg = false;
|
||||
d_max_symbols_without_valid_frame = GPS_L5_CNAV_DATA_PAGE_BITS * GPS_L5_SAMPLES_PER_SYMBOL * GPS_L5_SYMBOLS_PER_BIT * 5; //rise alarm if 5 consecutive subframes have no valid CRC
|
||||
d_max_symbols_without_valid_frame = GPS_L5_CNAV_DATA_PAGE_BITS * GPS_L5_SAMPLES_PER_SYMBOL * GPS_L5_SYMBOLS_PER_BIT * 20; //rise alarm if 20 consecutive subframes have no valid CRC
|
||||
|
||||
// initialize internal vars
|
||||
d_dump = dump;
|
||||
|
@ -113,8 +113,7 @@ BeidouB1iDllPllTracking::BeidouB1iDllPllTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
float early_late_space_chips = configuration->property(role + ".early_late_space_chips", 0.5);
|
||||
trk_param.early_late_space_chips = early_late_space_chips;
|
||||
@ -152,30 +151,12 @@ BeidouB1iDllPllTracking::BeidouB1iDllPllTracking(
|
||||
trk_param.system = 'C';
|
||||
char sig_[3] = "B1";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20)
|
||||
{
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
}
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
||||
if (FLAGS_cn0_min != 25)
|
||||
{
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
}
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50)
|
||||
{
|
||||
max_lock_fail = FLAGS_max_lock_fail;
|
||||
}
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.85);
|
||||
if (FLAGS_carrier_lock_th != 0.85)
|
||||
{
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
}
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -108,8 +108,7 @@ BeidouB3iDllPllTracking::BeidouB3iDllPllTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
float early_late_space_chips = configuration->property(role + ".early_late_space_chips", 0.5);
|
||||
trk_param.early_late_space_chips = early_late_space_chips;
|
||||
@ -147,18 +146,11 @@ BeidouB3iDllPllTracking::BeidouB3iDllPllTracking(
|
||||
trk_param.system = 'C';
|
||||
char sig_[3] = "B3";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20) cn0_samples = FLAGS_cn0_samples;
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
||||
if (FLAGS_cn0_min != 25) cn0_min = FLAGS_cn0_min;
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50) max_lock_fail = FLAGS_max_lock_fail;
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.85);
|
||||
if (FLAGS_carrier_lock_th != 0.85) carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -128,8 +128,7 @@ GalileoE1DllPllVemlTracking::GalileoE1DllPllVemlTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
int extend_correlation_symbols = configuration->property(role + ".extend_correlation_symbols", 1);
|
||||
float early_late_space_chips = configuration->property(role + ".early_late_space_chips", 0.15);
|
||||
@ -162,30 +161,11 @@ GalileoE1DllPllVemlTracking::GalileoE1DllPllVemlTracking(
|
||||
trk_param.system = 'E';
|
||||
char sig_[3] = "1B";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20)
|
||||
{
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
}
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
||||
if (FLAGS_cn0_min != 25)
|
||||
{
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
}
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50)
|
||||
{
|
||||
max_lock_fail = FLAGS_max_lock_fail;
|
||||
}
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.85);
|
||||
if (FLAGS_carrier_lock_th != 0.85)
|
||||
{
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
}
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -123,8 +123,7 @@ GalileoE5aDllPllTracking::GalileoE5aDllPllTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
float pll_bw_narrow_hz = configuration->property(role + ".pll_bw_narrow_hz", 5.0);
|
||||
trk_param.pll_bw_narrow_hz = pll_bw_narrow_hz;
|
||||
@ -135,7 +134,7 @@ GalileoE5aDllPllTracking::GalileoE5aDllPllTracking(
|
||||
int vector_length = std::round(fs_in / (GALILEO_E5A_CODE_CHIP_RATE_HZ / GALILEO_E5A_CODE_LENGTH_CHIPS));
|
||||
trk_param.vector_length = vector_length;
|
||||
int extend_correlation_symbols = configuration->property(role + ".extend_correlation_symbols", 1);
|
||||
float early_late_space_narrow_chips = configuration->property(role + ".early_late_space_narrow_chips", 0.15);
|
||||
float early_late_space_narrow_chips = configuration->property(role + ".early_late_space_narrow_chips", 0.5);
|
||||
trk_param.early_late_space_narrow_chips = early_late_space_narrow_chips;
|
||||
bool track_pilot = configuration->property(role + ".track_pilot", false);
|
||||
if (extend_correlation_symbols < 1)
|
||||
@ -159,30 +158,11 @@ GalileoE5aDllPllTracking::GalileoE5aDllPllTracking(
|
||||
trk_param.system = 'E';
|
||||
char sig_[3] = "5X";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20)
|
||||
{
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
}
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
||||
if (FLAGS_cn0_min != 25)
|
||||
{
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
}
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50)
|
||||
{
|
||||
max_lock_fail = FLAGS_max_lock_fail;
|
||||
}
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.85);
|
||||
if (FLAGS_carrier_lock_th != 0.85)
|
||||
{
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
}
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -129,8 +129,7 @@ GpsL1CaDllPllTracking::GpsL1CaDllPllTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
float early_late_space_chips = configuration->property(role + ".early_late_space_chips", 0.5);
|
||||
trk_param.early_late_space_chips = early_late_space_chips;
|
||||
@ -165,30 +164,11 @@ GpsL1CaDllPllTracking::GpsL1CaDllPllTracking(
|
||||
trk_param.system = 'G';
|
||||
char sig_[3] = "1C";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20)
|
||||
{
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
}
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 30);
|
||||
if (FLAGS_cn0_min != 25)
|
||||
{
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
}
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50)
|
||||
{
|
||||
max_lock_fail = FLAGS_max_lock_fail;
|
||||
}
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.80);
|
||||
if (FLAGS_carrier_lock_th != 0.85)
|
||||
{
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
}
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -117,8 +117,7 @@ GpsL2MDllPllTracking::GpsL2MDllPllTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
int vector_length = std::round(static_cast<double>(fs_in) / (static_cast<double>(GPS_L2_M_CODE_RATE_HZ) / static_cast<double>(GPS_L2_M_CODE_LENGTH_CHIPS)));
|
||||
trk_param.vector_length = vector_length;
|
||||
@ -141,30 +140,11 @@ GpsL2MDllPllTracking::GpsL2MDllPllTracking(
|
||||
trk_param.system = 'G';
|
||||
char sig_[3] = "2S";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20)
|
||||
{
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
}
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
||||
if (FLAGS_cn0_min != 25)
|
||||
{
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
}
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50)
|
||||
{
|
||||
max_lock_fail = FLAGS_max_lock_fail;
|
||||
}
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.85);
|
||||
if (FLAGS_carrier_lock_th != 0.85)
|
||||
{
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
}
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -130,13 +130,12 @@ GpsL5DllPllTracking::GpsL5DllPllTracking(
|
||||
trk_param.enable_fll_pull_in = enable_fll_pull_in;
|
||||
float fll_bw_hz = configuration->property(role + ".fll_bw_hz", 35.0);
|
||||
trk_param.fll_bw_hz = fll_bw_hz;
|
||||
float pull_in_time_s = configuration->property(role + ".pull_in_time_s", 2.0);
|
||||
trk_param.pull_in_time_s = pull_in_time_s;
|
||||
trk_param.pull_in_time_s = configuration->property(role + ".pull_in_time_s", trk_param.pull_in_time_s);
|
||||
|
||||
int vector_length = std::round(static_cast<double>(fs_in) / (static_cast<double>(GPS_L5I_CODE_RATE_HZ) / static_cast<double>(GPS_L5I_CODE_LENGTH_CHIPS)));
|
||||
trk_param.vector_length = vector_length;
|
||||
int extend_correlation_symbols = configuration->property(role + ".extend_correlation_symbols", 1);
|
||||
float early_late_space_narrow_chips = configuration->property(role + ".early_late_space_narrow_chips", 0.15);
|
||||
float early_late_space_narrow_chips = configuration->property(role + ".early_late_space_narrow_chips", 0.5);
|
||||
trk_param.early_late_space_narrow_chips = early_late_space_narrow_chips;
|
||||
bool track_pilot = configuration->property(role + ".track_pilot", false);
|
||||
if (extend_correlation_symbols < 1)
|
||||
@ -160,30 +159,12 @@ GpsL5DllPllTracking::GpsL5DllPllTracking(
|
||||
trk_param.system = 'G';
|
||||
char sig_[3] = "L5";
|
||||
std::memcpy(trk_param.signal, sig_, 3);
|
||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||
if (FLAGS_cn0_samples != 20)
|
||||
{
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
}
|
||||
trk_param.cn0_samples = cn0_samples;
|
||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
||||
if (FLAGS_cn0_min != 25)
|
||||
{
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
}
|
||||
trk_param.cn0_min = cn0_min;
|
||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||
if (FLAGS_max_lock_fail != 50)
|
||||
{
|
||||
max_lock_fail = FLAGS_max_lock_fail;
|
||||
}
|
||||
trk_param.max_lock_fail = max_lock_fail;
|
||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.75);
|
||||
if (FLAGS_carrier_lock_th != 0.85)
|
||||
{
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
}
|
||||
trk_param.carrier_lock_th = carrier_lock_th;
|
||||
|
||||
trk_param.cn0_samples = configuration->property(role + ".cn0_samples", trk_param.cn0_samples);
|
||||
trk_param.cn0_min = configuration->property(role + ".cn0_min", trk_param.cn0_min);
|
||||
trk_param.max_code_lock_fail = configuration->property(role + ".max_lock_fail", trk_param.max_code_lock_fail);
|
||||
trk_param.max_carrier_lock_fail = configuration->property(role + ".max_carrier_lock_fail", trk_param.max_carrier_lock_fail);
|
||||
trk_param.carrier_lock_th = configuration->property(role + ".carrier_lock_th", trk_param.carrier_lock_th);
|
||||
|
||||
//################# MAKE TRACKING GNURadio object ###################
|
||||
if (item_type == "gr_complex")
|
||||
|
@ -78,6 +78,9 @@ add_library(tracking_gr_blocks
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(tracking_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(tracking_gr_blocks PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(tracking_gr_blocks PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(tracking_gr_blocks PRIVATE Boost::filesystem)
|
||||
|
@ -65,10 +65,16 @@
|
||||
#include <exception> // for exception
|
||||
#include <iostream> // for cout, cerr
|
||||
#include <map>
|
||||
#include <numeric>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/path.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
@ -94,6 +100,7 @@ dll_pll_veml_tracking::dll_pll_veml_tracking(const Dll_Pll_Conf &conf_) : gr::bl
|
||||
this->set_msg_handler(pmt::mp("telemetry_to_trk"), boost::bind(&dll_pll_veml_tracking::msg_handler_telemetry_to_trk, this, _1));
|
||||
|
||||
// initialize internal vars
|
||||
d_dll_filt_history.set_capacity(2000);
|
||||
d_veml = false;
|
||||
d_cloop = true;
|
||||
d_pull_in_transitory = true;
|
||||
@ -444,6 +451,7 @@ dll_pll_veml_tracking::dll_pll_veml_tracking(const Dll_Pll_Conf &conf_) : gr::bl
|
||||
d_carrier_lock_test = 1.0;
|
||||
d_CN0_SNV_dB_Hz = 0.0;
|
||||
d_carrier_lock_fail_counter = 0;
|
||||
d_code_lock_fail_counter = 0;
|
||||
d_carrier_lock_threshold = trk_parameters.carrier_lock_th;
|
||||
d_Prompt_Data = static_cast<gr_complex *>(volk_gnsssdr_malloc(sizeof(gr_complex), volk_gnsssdr_get_alignment()));
|
||||
d_cn0_smoother = Exponential_Smoother();
|
||||
@ -451,6 +459,13 @@ dll_pll_veml_tracking::dll_pll_veml_tracking(const Dll_Pll_Conf &conf_) : gr::bl
|
||||
{
|
||||
d_cn0_smoother.set_samples_for_initialization(200 / static_cast<int>(d_code_period * 1000.0));
|
||||
}
|
||||
|
||||
d_carrier_lock_test_smoother = Exponential_Smoother();
|
||||
d_carrier_lock_test_smoother.set_alpha(0.002);
|
||||
d_carrier_lock_test_smoother.set_min_value(-1.0);
|
||||
d_carrier_lock_test_smoother.set_offset(0.0);
|
||||
d_carrier_lock_test_smoother.set_samples_for_initialization(25);
|
||||
|
||||
d_acquisition_gnss_synchro = nullptr;
|
||||
d_channel = 0;
|
||||
d_acq_code_phase_samples = 0.0;
|
||||
@ -512,6 +527,7 @@ dll_pll_veml_tracking::dll_pll_veml_tracking(const Dll_Pll_Conf &conf_) : gr::bl
|
||||
d_dump = false;
|
||||
}
|
||||
}
|
||||
d_corrected_doppler = false;
|
||||
}
|
||||
|
||||
|
||||
@ -540,7 +556,7 @@ void dll_pll_veml_tracking::msg_handler_telemetry_to_trk(const pmt::pmt_t &msg)
|
||||
{
|
||||
DLOG(INFO) << "Telemetry fault received in ch " << this->d_channel;
|
||||
gr::thread::scoped_lock lock(d_setlock);
|
||||
d_carrier_lock_fail_counter = 10000; //force loss-of-lock condition
|
||||
d_carrier_lock_fail_counter = 100000; //force loss-of-lock condition
|
||||
break;
|
||||
}
|
||||
default:
|
||||
@ -717,6 +733,7 @@ void dll_pll_veml_tracking::start_tracking()
|
||||
std::fill_n(d_correlator_outs, d_n_correlator_taps, gr_complex(0.0, 0.0));
|
||||
|
||||
d_carrier_lock_fail_counter = 0;
|
||||
d_code_lock_fail_counter = 0;
|
||||
d_rem_code_phase_samples = 0.0;
|
||||
d_rem_carr_phase_rad = 0.0;
|
||||
d_rem_code_phase_chips = 0.0;
|
||||
@ -757,6 +774,7 @@ void dll_pll_veml_tracking::start_tracking()
|
||||
d_cloop = true;
|
||||
d_pull_in_transitory = true;
|
||||
d_Prompt_circular_buffer.clear();
|
||||
d_corrected_doppler = false;
|
||||
}
|
||||
|
||||
|
||||
@ -866,11 +884,13 @@ bool dll_pll_veml_tracking::cn0_and_tracking_lock_status(double coh_integration_
|
||||
float d_CN0_SNV_dB_Hz_raw = cn0_svn_estimator(d_Prompt_buffer, trk_parameters.cn0_samples, static_cast<float>(coh_integration_time_s));
|
||||
d_CN0_SNV_dB_Hz = d_cn0_smoother.smooth(d_CN0_SNV_dB_Hz_raw);
|
||||
// Carrier lock indicator
|
||||
d_carrier_lock_test = carrier_lock_detector(d_Prompt_buffer, trk_parameters.cn0_samples);
|
||||
d_carrier_lock_test = d_carrier_lock_test_smoother.smooth(carrier_lock_detector(d_Prompt_buffer, 1));
|
||||
//d_carrier_lock_test = carrier_lock_detector(d_Prompt_buffer, trk_parameters.cn0_samples);
|
||||
// Loss of lock detection
|
||||
if (!d_pull_in_transitory)
|
||||
{
|
||||
if (d_carrier_lock_test < d_carrier_lock_threshold or d_CN0_SNV_dB_Hz < trk_parameters.cn0_min)
|
||||
//d_carrier_lock_test < d_carrier_lock_threshold or
|
||||
if (d_carrier_lock_test < d_carrier_lock_threshold)
|
||||
{
|
||||
d_carrier_lock_fail_counter++;
|
||||
}
|
||||
@ -881,13 +901,28 @@ bool dll_pll_veml_tracking::cn0_and_tracking_lock_status(double coh_integration_
|
||||
d_carrier_lock_fail_counter--;
|
||||
}
|
||||
}
|
||||
|
||||
if (d_CN0_SNV_dB_Hz < trk_parameters.cn0_min)
|
||||
{
|
||||
d_code_lock_fail_counter++;
|
||||
}
|
||||
if (d_carrier_lock_fail_counter > trk_parameters.max_lock_fail)
|
||||
else
|
||||
{
|
||||
if (d_code_lock_fail_counter > 0)
|
||||
{
|
||||
d_code_lock_fail_counter--;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (d_carrier_lock_fail_counter > trk_parameters.max_carrier_lock_fail or d_code_lock_fail_counter > trk_parameters.max_code_lock_fail)
|
||||
{
|
||||
std::cout << "Loss of lock in channel " << d_channel << "!" << std::endl;
|
||||
LOG(INFO) << "Loss of lock in channel " << d_channel << "!";
|
||||
LOG(INFO) << "Loss of lock in channel " << d_channel
|
||||
<< " (carrier_lock_fail_counter:" << d_carrier_lock_fail_counter
|
||||
<< " code_lock_fail_counter : " << d_code_lock_fail_counter << ")";
|
||||
this->message_port_pub(pmt::mp("events"), pmt::from_long(3)); // 3 -> loss of lock
|
||||
d_carrier_lock_fail_counter = 0;
|
||||
d_code_lock_fail_counter = 0;
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
@ -985,9 +1020,25 @@ void dll_pll_veml_tracking::run_dll_pll()
|
||||
}
|
||||
// Code discriminator filter
|
||||
d_code_error_filt_chips = d_code_loop_filter.apply(d_code_error_chips); // [chips/second]
|
||||
|
||||
// New code Doppler frequency estimation
|
||||
d_code_freq_chips = (1.0 + (d_carrier_doppler_hz / d_signal_carrier_freq)) * d_code_chip_rate - d_code_error_filt_chips;
|
||||
|
||||
// Experimental: detect Carrier Doppler vs. Code Doppler incoherence and correct the Carrier Doppler
|
||||
if (d_pull_in_transitory == false and d_corrected_doppler == false)
|
||||
{
|
||||
d_dll_filt_history.push_back(static_cast<float>(d_code_error_filt_chips));
|
||||
if (d_dll_filt_history.full())
|
||||
{
|
||||
float avg_code_error_chips_s = std::accumulate(d_dll_filt_history.begin(), d_dll_filt_history.end(), 0) / static_cast<float>(d_dll_filt_history.capacity());
|
||||
if (fabs(avg_code_error_chips_s) > 1.0)
|
||||
{
|
||||
float carrier_doppler_error_hz = static_cast<float>(d_signal_carrier_freq) * avg_code_error_chips_s / static_cast<float>(d_code_chip_rate);
|
||||
LOG(INFO) << "Detected and corrected carrier doppler error: " << carrier_doppler_error_hz << " [Hz] on sat " << Gnss_Satellite(systemName, d_acquisition_gnss_synchro->PRN);
|
||||
d_carrier_loop_filter.initialize(d_carrier_doppler_hz - carrier_doppler_error_hz);
|
||||
d_corrected_doppler = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1573,6 +1624,8 @@ int dll_pll_veml_tracking::general_work(int noutput_items __attribute__((unused)
|
||||
if (trk_parameters.pull_in_time_s < (d_sample_counter - d_acq_sample_stamp) / static_cast<int>(trk_parameters.fs_in))
|
||||
{
|
||||
d_pull_in_transitory = false;
|
||||
d_carrier_lock_fail_counter = 0;
|
||||
d_code_lock_fail_counter = 0;
|
||||
}
|
||||
}
|
||||
switch (d_state)
|
||||
@ -1606,8 +1659,9 @@ int dll_pll_veml_tracking::general_work(int noutput_items __attribute__((unused)
|
||||
d_state = 2;
|
||||
d_sample_counter += samples_offset; // count for the processed samples
|
||||
d_cn0_smoother.reset();
|
||||
d_carrier_lock_test_smoother.reset();
|
||||
|
||||
DLOG(INFO) << "Number of samples between Acquisition and Tracking = " << acq_trk_diff_samples << " ( " << acq_trk_diff_seconds << " s)";
|
||||
LOG(INFO) << "Number of samples between Acquisition and Tracking = " << acq_trk_diff_samples << " ( " << acq_trk_diff_seconds << " s)";
|
||||
DLOG(INFO) << "PULL-IN Doppler [Hz] = " << d_carrier_doppler_hz
|
||||
<< ". PULL-IN Code Phase [samples] = " << d_acq_code_phase_samples;
|
||||
|
||||
@ -1642,6 +1696,9 @@ int dll_pll_veml_tracking::general_work(int noutput_items __attribute__((unused)
|
||||
|
||||
// enable write dump file this cycle (valid DLL/PLL cycle)
|
||||
log_data(false);
|
||||
|
||||
if (!d_pull_in_transitory)
|
||||
{
|
||||
if (d_secondary)
|
||||
{
|
||||
// ####### SECONDARY CODE LOCK #####
|
||||
@ -1702,7 +1759,11 @@ int dll_pll_veml_tracking::general_work(int noutput_items __attribute__((unused)
|
||||
{
|
||||
next_state = true;
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
next_state = false; //keep in state 2 during pull-in transitory
|
||||
}
|
||||
// ########### Output the tracking results to Telemetry block ##########
|
||||
if (interchange_iq)
|
||||
{
|
||||
@ -1837,7 +1898,6 @@ int dll_pll_veml_tracking::general_work(int noutput_items __attribute__((unused)
|
||||
d_extend_correlation_symbols_count = 0;
|
||||
d_state = 4;
|
||||
}
|
||||
log_data(true);
|
||||
break;
|
||||
}
|
||||
case 4: // narrow tracking
|
||||
|
@ -113,6 +113,8 @@ private:
|
||||
int32_t d_preamble_length_symbols;
|
||||
boost::circular_buffer<float> d_symbol_history;
|
||||
|
||||
// dll filter buffer
|
||||
boost::circular_buffer<float> d_dll_filt_history;
|
||||
// tracking state machine
|
||||
int32_t d_state;
|
||||
|
||||
@ -170,6 +172,7 @@ private:
|
||||
|
||||
// tracking vars
|
||||
bool d_pull_in_transitory;
|
||||
bool d_corrected_doppler;
|
||||
double d_current_correlation_time_s;
|
||||
double d_carr_phase_error_hz;
|
||||
double d_carr_freq_error_hz;
|
||||
@ -193,13 +196,14 @@ private:
|
||||
// CN0 estimation and lock detector
|
||||
int32_t d_cn0_estimation_counter;
|
||||
int32_t d_carrier_lock_fail_counter;
|
||||
int32_t d_code_lock_fail_counter;
|
||||
double d_carrier_lock_test;
|
||||
double d_CN0_SNV_dB_Hz;
|
||||
double d_carrier_lock_threshold;
|
||||
boost::circular_buffer<gr_complex> d_Prompt_circular_buffer;
|
||||
gr_complex *d_Prompt_buffer;
|
||||
Exponential_Smoother d_cn0_smoother;
|
||||
|
||||
Exponential_Smoother d_carrier_lock_test_smoother;
|
||||
// file dump
|
||||
std::ofstream d_dump_file;
|
||||
std::string d_dump_filename;
|
||||
|
@ -60,8 +60,13 @@
|
||||
#include <map>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/path.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -63,6 +63,12 @@ set(TRACKING_LIB_HEADERS
|
||||
exponential_smoother.h
|
||||
)
|
||||
|
||||
if(ARMADILLO_VERSION_STRING VERSION_GREATER 7.400)
|
||||
# sqrtmat_sympd() requires 7.400
|
||||
set(TRACKING_LIB_SOURCES ${TRACKING_LIB_SOURCES} nonlinear_tracking.cc)
|
||||
set(TRACKING_LIB_HEADERS ${TRACKING_LIB_HEADERS} nonlinear_tracking.h)
|
||||
endif()
|
||||
|
||||
if(ENABLE_FPGA)
|
||||
set(TRACKING_LIB_SOURCES ${TRACKING_LIB_SOURCES} fpga_multicorrelator.cc dll_pll_conf_fpga.cc)
|
||||
set(TRACKING_LIB_HEADERS ${TRACKING_LIB_HEADERS} fpga_multicorrelator.h dll_pll_conf_fpga.h)
|
||||
@ -82,6 +88,7 @@ target_link_libraries(tracking_libs
|
||||
Gnuradio::runtime
|
||||
Volkgnsssdr::volkgnsssdr
|
||||
core_system_parameters
|
||||
algorithms_libs
|
||||
${OPT_TRACKING_LIBRARIES}
|
||||
PRIVATE
|
||||
Gflags::gflags
|
||||
|
@ -31,6 +31,7 @@
|
||||
|
||||
|
||||
#include "dll_pll_conf.h"
|
||||
#include "gnss_sdr_flags.h"
|
||||
#include <cstring>
|
||||
|
||||
Dll_Pll_Conf::Dll_Pll_Conf()
|
||||
@ -45,7 +46,7 @@ Dll_Pll_Conf::Dll_Pll_Conf()
|
||||
dump_filename = std::string("./dll_pll_dump.dat");
|
||||
enable_fll_pull_in = false;
|
||||
enable_fll_steady_state = false;
|
||||
pull_in_time_s = 2;
|
||||
pull_in_time_s = 10;
|
||||
fll_filter_order = 1;
|
||||
pll_filter_order = 3;
|
||||
dll_filter_order = 2;
|
||||
@ -61,11 +62,12 @@ Dll_Pll_Conf::Dll_Pll_Conf()
|
||||
early_late_space_narrow_chips = 0.1;
|
||||
very_early_late_space_narrow_chips = 0.1;
|
||||
extend_correlation_symbols = 5;
|
||||
cn0_samples = 20;
|
||||
carrier_lock_det_mav_samples = 20;
|
||||
cn0_min = 25;
|
||||
max_lock_fail = 50;
|
||||
carrier_lock_th = 0.85;
|
||||
cn0_samples = FLAGS_cn0_samples;
|
||||
carrier_lock_det_mav_samples = FLAGS_cn0_samples;
|
||||
cn0_min = FLAGS_cn0_min;
|
||||
max_carrier_lock_fail = FLAGS_max_carrier_lock_fail;
|
||||
max_code_lock_fail = FLAGS_max_lock_fail;
|
||||
carrier_lock_th = FLAGS_carrier_lock_th;
|
||||
track_pilot = false;
|
||||
system = 'G';
|
||||
char sig_[3] = "1C";
|
||||
|
@ -69,7 +69,8 @@ public:
|
||||
int32_t cn0_samples;
|
||||
int32_t carrier_lock_det_mav_samples;
|
||||
int32_t cn0_min;
|
||||
int32_t max_lock_fail;
|
||||
int32_t max_code_lock_fail;
|
||||
int32_t max_carrier_lock_fail;
|
||||
uint32_t smoother_length;
|
||||
double carrier_lock_th;
|
||||
bool track_pilot;
|
||||
|
390
src/algorithms/tracking/libs/nonlinear_tracking.cc
Normal file
390
src/algorithms/tracking/libs/nonlinear_tracking.cc
Normal file
@ -0,0 +1,390 @@
|
||||
/*!
|
||||
* \file cubature_filter.cc
|
||||
* \brief Interface of a library for nonlinear tracking algorithms
|
||||
*
|
||||
* Cubature_Filter implements the functionality of the Cubature Kalman
|
||||
* Filter, which uses multidimensional cubature rules to estimate the
|
||||
* time evolution of a nonlinear system. UnscentedFilter implements
|
||||
* an Unscented Kalman Filter which uses Unscented Transform rules to
|
||||
* perform a similar estimation.
|
||||
*
|
||||
* [1] I Arasaratnam and S Haykin. Cubature kalman filters. IEEE
|
||||
* Transactions on Automatic Control, 54(6):1254–1269,2009.
|
||||
*
|
||||
* \authors <ul>
|
||||
* <li> Gerald LaMountain, 2019. gerald(at)ece.neu.edu
|
||||
* <li> Jordi Vila-Valls 2019. jvila(at)cttc.es
|
||||
* </ul>
|
||||
* -------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (C) 2010-2019 (see AUTHORS file for a list of contributors)
|
||||
*
|
||||
* GNSS-SDR is a software defined Global Navigation
|
||||
* Satellite Systems receiver
|
||||
*
|
||||
* This file is part of GNSS-SDR.
|
||||
*
|
||||
* GNSS-SDR is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNSS-SDR is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include "nonlinear_tracking.h"
|
||||
|
||||
/***************** CUBATURE KALMAN FILTER *****************/
|
||||
|
||||
CubatureFilter::CubatureFilter()
|
||||
{
|
||||
int nx = 1;
|
||||
x_pred_out = arma::zeros(nx, 1);
|
||||
P_x_pred_out = arma::eye(nx, nx) * (nx + 1);
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
CubatureFilter::CubatureFilter(int nx)
|
||||
{
|
||||
x_pred_out = arma::zeros(nx, 1);
|
||||
P_x_pred_out = arma::eye(nx, nx) * (nx + 1);
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
CubatureFilter::CubatureFilter(const arma::vec& x_pred_0, const arma::mat& P_x_pred_0)
|
||||
{
|
||||
x_pred_out = x_pred_0;
|
||||
P_x_pred_out = P_x_pred_0;
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
CubatureFilter::~CubatureFilter() = default;
|
||||
|
||||
|
||||
void CubatureFilter::initialize(const arma::mat& x_pred_0, const arma::mat& P_x_pred_0)
|
||||
{
|
||||
x_pred_out = x_pred_0;
|
||||
P_x_pred_out = P_x_pred_0;
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Perform the prediction step of the cubature Kalman filter
|
||||
*/
|
||||
void CubatureFilter::predict_sequential(const arma::vec& x_post, const arma::mat& P_x_post, ModelFunction* transition_fcn, const arma::mat& noise_covariance)
|
||||
{
|
||||
// Compute number of cubature points
|
||||
int nx = x_post.n_elem;
|
||||
int np = 2 * nx;
|
||||
|
||||
// Generator Matrix
|
||||
arma::mat gen_one = arma::join_horiz(arma::eye(nx, nx), -1.0 * arma::eye(nx, nx));
|
||||
|
||||
// Initialize predicted mean and covariance
|
||||
arma::vec x_pred = arma::zeros(nx, 1);
|
||||
arma::mat P_x_pred = arma::zeros(nx, nx);
|
||||
|
||||
// Factorize posterior covariance
|
||||
arma::mat Sm_post = arma::chol(P_x_post, "lower");
|
||||
|
||||
// Propagate and evaluate cubature points
|
||||
arma::vec Xi_post;
|
||||
arma::vec Xi_pred;
|
||||
|
||||
for (uint8_t i = 0; i < np; i++)
|
||||
{
|
||||
Xi_post = Sm_post * (std::sqrt(static_cast<float>(np) / 2.0) * gen_one.col(i)) + x_post;
|
||||
Xi_pred = (*transition_fcn)(Xi_post);
|
||||
|
||||
x_pred = x_pred + Xi_pred;
|
||||
P_x_pred = P_x_pred + Xi_pred * Xi_pred.t();
|
||||
}
|
||||
|
||||
// Compute predicted mean and error covariance
|
||||
x_pred = x_pred / static_cast<float>(np);
|
||||
P_x_pred = P_x_pred / static_cast<float>(np) - x_pred * x_pred.t() + noise_covariance;
|
||||
|
||||
// Store predicted mean and error covariance
|
||||
x_pred_out = x_pred;
|
||||
P_x_pred_out = P_x_pred;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Perform the update step of the cubature Kalman filter
|
||||
*/
|
||||
void CubatureFilter::update_sequential(const arma::vec& z_upd, const arma::vec& x_pred, const arma::mat& P_x_pred, ModelFunction* measurement_fcn, const arma::mat& noise_covariance)
|
||||
{
|
||||
// Compute number of cubature points
|
||||
int nx = x_pred.n_elem;
|
||||
int nz = z_upd.n_elem;
|
||||
int np = 2 * nx;
|
||||
|
||||
// Generator Matrix
|
||||
arma::mat gen_one = arma::join_horiz(arma::eye(nx, nx), -1.0 * arma::eye(nx, nx));
|
||||
|
||||
// Initialize estimated predicted measurement and covariances
|
||||
arma::mat z_pred = arma::zeros(nz, 1);
|
||||
arma::mat P_zz_pred = arma::zeros(nz, nz);
|
||||
arma::mat P_xz_pred = arma::zeros(nx, nz);
|
||||
|
||||
// Factorize predicted covariance
|
||||
arma::mat Sm_pred = arma::chol(P_x_pred, "lower");
|
||||
|
||||
// Propagate and evaluate cubature points
|
||||
arma::vec Xi_pred;
|
||||
arma::vec Zi_pred;
|
||||
for (uint8_t i = 0; i < np; i++)
|
||||
{
|
||||
Xi_pred = Sm_pred * (std::sqrt(static_cast<float>(np) / 2.0) * gen_one.col(i)) + x_pred;
|
||||
Zi_pred = (*measurement_fcn)(Xi_pred);
|
||||
|
||||
z_pred = z_pred + Zi_pred;
|
||||
P_zz_pred = P_zz_pred + Zi_pred * Zi_pred.t();
|
||||
P_xz_pred = P_xz_pred + Xi_pred * Zi_pred.t();
|
||||
}
|
||||
|
||||
// Compute measurement mean, covariance and cross covariance
|
||||
z_pred = z_pred / static_cast<float>(np);
|
||||
P_zz_pred = P_zz_pred / static_cast<float>(np) - z_pred * z_pred.t() + noise_covariance;
|
||||
P_xz_pred = P_xz_pred / static_cast<float>(np) - x_pred * z_pred.t();
|
||||
|
||||
// Compute cubature Kalman gain
|
||||
arma::mat W_k = P_xz_pred * arma::inv(P_zz_pred);
|
||||
|
||||
// Compute and store the updated mean and error covariance
|
||||
x_est = x_pred + W_k * (z_upd - z_pred);
|
||||
P_x_est = P_x_pred - W_k * P_zz_pred * W_k.t();
|
||||
}
|
||||
|
||||
|
||||
arma::mat CubatureFilter::get_x_pred() const
|
||||
{
|
||||
return x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
arma::mat CubatureFilter::get_P_x_pred() const
|
||||
{
|
||||
return P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
arma::mat CubatureFilter::get_x_est() const
|
||||
{
|
||||
return x_est;
|
||||
}
|
||||
|
||||
|
||||
arma::mat CubatureFilter::get_P_x_est() const
|
||||
{
|
||||
return P_x_est;
|
||||
}
|
||||
/***************** END CUBATURE KALMAN FILTER *****************/
|
||||
|
||||
|
||||
/***************** UNSCENTED KALMAN FILTER *****************/
|
||||
|
||||
UnscentedFilter::UnscentedFilter()
|
||||
{
|
||||
int nx = 1;
|
||||
x_pred_out = arma::zeros(nx, 1);
|
||||
P_x_pred_out = arma::eye(nx, nx) * (nx + 1);
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
UnscentedFilter::UnscentedFilter(int nx)
|
||||
{
|
||||
x_pred_out = arma::zeros(nx, 1);
|
||||
P_x_pred_out = arma::eye(nx, nx) * (nx + 1);
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
UnscentedFilter::UnscentedFilter(const arma::vec& x_pred_0, const arma::mat& P_x_pred_0)
|
||||
{
|
||||
x_pred_out = x_pred_0;
|
||||
P_x_pred_out = P_x_pred_0;
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
UnscentedFilter::~UnscentedFilter() = default;
|
||||
|
||||
|
||||
void UnscentedFilter::initialize(const arma::mat& x_pred_0, const arma::mat& P_x_pred_0)
|
||||
{
|
||||
x_pred_out = x_pred_0;
|
||||
P_x_pred_out = P_x_pred_0;
|
||||
|
||||
x_est = x_pred_out;
|
||||
P_x_est = P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Perform the prediction step of the Unscented Kalman filter
|
||||
*/
|
||||
void UnscentedFilter::predict_sequential(const arma::vec& x_post, const arma::mat& P_x_post, ModelFunction* transition_fcn, const arma::mat& noise_covariance)
|
||||
{
|
||||
// Compute number of sigma points
|
||||
int nx = x_post.n_elem;
|
||||
int np = 2 * nx + 1;
|
||||
|
||||
float alpha = 0.001;
|
||||
float kappa = 0.0;
|
||||
float beta = 2.0;
|
||||
|
||||
float lambda = std::pow(alpha, 2.0) * (static_cast<float>(nx) + kappa) - static_cast<float>(nx);
|
||||
|
||||
// Compute UT Weights
|
||||
float W0_m = lambda / (static_cast<float>(nx) + lambda);
|
||||
float W0_c = lambda / (static_cast<float>(nx) + lambda) + (1 - std::pow(alpha, 2.0) + beta);
|
||||
float Wi_m = 1.0 / (2.0 * (static_cast<float>(nx) + lambda));
|
||||
|
||||
// Propagate and evaluate sigma points
|
||||
arma::mat Xi_fact = arma::zeros(nx, nx);
|
||||
arma::mat Xi_post = arma::zeros(nx, np);
|
||||
arma::mat Xi_pred = arma::zeros(nx, np);
|
||||
|
||||
|
||||
Xi_post.col(0) = x_post;
|
||||
Xi_pred.col(0) = (*transition_fcn)(Xi_post.col(0));
|
||||
for (uint8_t i = 1; i <= nx; i++)
|
||||
{
|
||||
Xi_fact = std::sqrt(static_cast<float>(nx) + lambda) * arma::sqrtmat_sympd(P_x_post);
|
||||
Xi_post.col(i) = x_post + Xi_fact.col(i - 1);
|
||||
Xi_post.col(i + nx) = x_post - Xi_fact.col(i - 1);
|
||||
|
||||
Xi_pred.col(i) = (*transition_fcn)(Xi_post.col(i));
|
||||
Xi_pred.col(i + nx) = (*transition_fcn)(Xi_post.col(i + nx));
|
||||
}
|
||||
|
||||
// Compute predicted mean
|
||||
arma::vec x_pred = W0_m * Xi_pred.col(0) + Wi_m * arma::sum(Xi_pred.cols(1, np - 1), 1);
|
||||
|
||||
// Compute predicted error covariance
|
||||
arma::mat P_x_pred = W0_c * ((Xi_pred.col(0) - x_pred) * (Xi_pred.col(0).t() - x_pred.t()));
|
||||
for (uint8_t i = 1; i < np; i++)
|
||||
{
|
||||
P_x_pred = P_x_pred + Wi_m * ((Xi_pred.col(i) - x_pred) * (Xi_pred.col(i).t() - x_pred.t()));
|
||||
}
|
||||
P_x_pred = P_x_pred + noise_covariance;
|
||||
|
||||
// Store predicted mean and error covariance
|
||||
x_pred_out = x_pred;
|
||||
P_x_pred_out = P_x_pred;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Perform the update step of the Unscented Kalman filter
|
||||
*/
|
||||
void UnscentedFilter::update_sequential(const arma::vec& z_upd, const arma::vec& x_pred, const arma::mat& P_x_pred, ModelFunction* measurement_fcn, const arma::mat& noise_covariance)
|
||||
{
|
||||
// Compute number of sigma points
|
||||
int nx = x_pred.n_elem;
|
||||
int nz = z_upd.n_elem;
|
||||
int np = 2 * nx + 1;
|
||||
|
||||
float alpha = 0.001;
|
||||
float kappa = 0.0;
|
||||
float beta = 2.0;
|
||||
|
||||
float lambda = std::pow(alpha, 2.0) * (static_cast<float>(nx) + kappa) - static_cast<float>(nx);
|
||||
|
||||
// Compute UT Weights
|
||||
float W0_m = lambda / (static_cast<float>(nx) + lambda);
|
||||
float W0_c = lambda / (static_cast<float>(nx) + lambda) + (1.0 - std::pow(alpha, 2.0) + beta);
|
||||
float Wi_m = 1.0 / (2.0 * (static_cast<float>(nx) + lambda));
|
||||
|
||||
// Propagate and evaluate sigma points
|
||||
arma::mat Xi_fact = arma::zeros(nx, nx);
|
||||
arma::mat Xi_pred = arma::zeros(nx, np);
|
||||
arma::mat Zi_pred = arma::zeros(nz, np);
|
||||
|
||||
Xi_pred.col(0) = x_pred;
|
||||
Zi_pred.col(0) = (*measurement_fcn)(Xi_pred.col(0));
|
||||
for (uint8_t i = 1; i <= nx; i++)
|
||||
{
|
||||
Xi_fact = std::sqrt(static_cast<float>(nx) + lambda) * arma::sqrtmat_sympd(P_x_pred);
|
||||
Xi_pred.col(i) = x_pred + Xi_fact.col(i - 1);
|
||||
Xi_pred.col(i + nx) = x_pred - Xi_fact.col(i - 1);
|
||||
|
||||
Zi_pred.col(i) = (*measurement_fcn)(Xi_pred.col(i));
|
||||
Zi_pred.col(i + nx) = (*measurement_fcn)(Xi_pred.col(i + nx));
|
||||
}
|
||||
|
||||
// Compute measurement mean
|
||||
arma::mat z_pred = W0_m * Zi_pred.col(0) + Wi_m * arma::sum(Zi_pred.cols(1, np - 1), 1);
|
||||
|
||||
// Compute measurement covariance and cross covariance
|
||||
arma::mat P_zz_pred = W0_c * ((Zi_pred.col(0) - z_pred) * (Zi_pred.col(0).t() - z_pred.t()));
|
||||
arma::mat P_xz_pred = W0_c * ((Xi_pred.col(0) - x_pred) * (Zi_pred.col(0).t() - z_pred.t()));
|
||||
for (uint8_t i = 0; i < np; i++)
|
||||
{
|
||||
P_zz_pred = P_zz_pred + Wi_m * ((Zi_pred.col(i) - z_pred) * (Zi_pred.col(i).t() - z_pred.t()));
|
||||
P_xz_pred = P_xz_pred + Wi_m * ((Xi_pred.col(i) - x_pred) * (Zi_pred.col(i).t() - z_pred.t()));
|
||||
}
|
||||
P_zz_pred = P_zz_pred + noise_covariance;
|
||||
|
||||
// Estimate cubature Kalman gain
|
||||
arma::mat W_k = P_xz_pred * arma::inv(P_zz_pred);
|
||||
|
||||
// Estimate and store the updated mean and error covariance
|
||||
x_est = x_pred + W_k * (z_upd - z_pred);
|
||||
P_x_est = P_x_pred - W_k * P_zz_pred * W_k.t();
|
||||
}
|
||||
|
||||
|
||||
arma::mat UnscentedFilter::get_x_pred() const
|
||||
{
|
||||
return x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
arma::mat UnscentedFilter::get_P_x_pred() const
|
||||
{
|
||||
return P_x_pred_out;
|
||||
}
|
||||
|
||||
|
||||
arma::mat UnscentedFilter::get_x_est() const
|
||||
{
|
||||
return x_est;
|
||||
}
|
||||
|
||||
|
||||
arma::mat UnscentedFilter::get_P_x_est() const
|
||||
{
|
||||
return P_x_est;
|
||||
}
|
||||
|
||||
/***************** END UNSCENTED KALMAN FILTER *****************/
|
116
src/algorithms/tracking/libs/nonlinear_tracking.h
Normal file
116
src/algorithms/tracking/libs/nonlinear_tracking.h
Normal file
@ -0,0 +1,116 @@
|
||||
/*!
|
||||
* \file nonlinear_tracking.h
|
||||
* \brief Interface of a library for nonlinear tracking algorithms
|
||||
*
|
||||
* CubatureFilter implements the functionality of the Cubature Kalman
|
||||
* Filter, which uses multidimensional cubature rules to estimate the
|
||||
* time evolution of a nonlinear system. UnscentedFilter implements
|
||||
* an Unscented Kalman Filter which uses Unscented Transform rules to
|
||||
* perform a similar estimation.
|
||||
*
|
||||
* [1] I Arasaratnam and S Haykin. Cubature kalman filters. IEEE
|
||||
* Transactions on Automatic Control, 54(6):1254–1269,2009.
|
||||
*
|
||||
* \authors <ul>
|
||||
* <li> Gerald LaMountain, 2019. gerald(at)ece.neu.edu
|
||||
* <li> Jordi Vila-Valls 2019. jvila(at)cttc.es
|
||||
* </ul>
|
||||
* -------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (C) 2010-2019 (see AUTHORS file for a list of contributors)
|
||||
*
|
||||
* GNSS-SDR is a software defined Global Navigation
|
||||
* Satellite Systems receiver
|
||||
*
|
||||
* This file is part of GNSS-SDR.
|
||||
*
|
||||
* GNSS-SDR is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNSS-SDR is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#ifndef GNSS_SDR_NONLINEAR_TRACKING_H_
|
||||
#define GNSS_SDR_NONLINEAR_TRACKING_H_
|
||||
|
||||
#include <armadillo>
|
||||
#include <gnuradio/gr_complex.h>
|
||||
|
||||
// Abstract model function
|
||||
class ModelFunction
|
||||
{
|
||||
public:
|
||||
ModelFunction(){};
|
||||
virtual arma::vec operator()(const arma::vec& input) = 0;
|
||||
virtual ~ModelFunction() = default;
|
||||
};
|
||||
|
||||
class CubatureFilter
|
||||
{
|
||||
public:
|
||||
// Constructors and destructors
|
||||
CubatureFilter();
|
||||
CubatureFilter(int nx);
|
||||
CubatureFilter(const arma::vec& x_pred_0, const arma::mat& P_x_pred_0);
|
||||
~CubatureFilter();
|
||||
|
||||
// Reinitialization function
|
||||
void initialize(const arma::mat& x_pred_0, const arma::mat& P_x_pred_0);
|
||||
|
||||
// Prediction and estimation
|
||||
void predict_sequential(const arma::vec& x_post, const arma::mat& P_x_post, ModelFunction* transition_fcn, const arma::mat& noise_covariance);
|
||||
void update_sequential(const arma::vec& z_upd, const arma::vec& x_pred, const arma::mat& P_x_pred, ModelFunction* measurement_fcn, const arma::mat& noise_covariance);
|
||||
|
||||
// Getters
|
||||
arma::mat get_x_pred() const;
|
||||
arma::mat get_P_x_pred() const;
|
||||
arma::mat get_x_est() const;
|
||||
arma::mat get_P_x_est() const;
|
||||
|
||||
private:
|
||||
arma::vec x_pred_out;
|
||||
arma::mat P_x_pred_out;
|
||||
arma::vec x_est;
|
||||
arma::mat P_x_est;
|
||||
};
|
||||
|
||||
class UnscentedFilter
|
||||
{
|
||||
public:
|
||||
// Constructors and destructors
|
||||
UnscentedFilter();
|
||||
UnscentedFilter(int nx);
|
||||
UnscentedFilter(const arma::vec& x_pred_0, const arma::mat& P_x_pred_0);
|
||||
~UnscentedFilter();
|
||||
|
||||
// Reinitialization function
|
||||
void initialize(const arma::mat& x_pred_0, const arma::mat& P_x_pred_0);
|
||||
|
||||
// Prediction and estimation
|
||||
void predict_sequential(const arma::vec& x_post, const arma::mat& P_x_post, ModelFunction* transition_fcn, const arma::mat& noise_covariance);
|
||||
void update_sequential(const arma::vec& z_upd, const arma::vec& x_pred, const arma::mat& P_x_pred, ModelFunction* measurement_fcn, const arma::mat& noise_covariance);
|
||||
|
||||
// Getters
|
||||
arma::mat get_x_pred() const;
|
||||
arma::mat get_P_x_pred() const;
|
||||
arma::mat get_x_est() const;
|
||||
arma::mat get_P_x_est() const;
|
||||
|
||||
private:
|
||||
arma::vec x_pred_out;
|
||||
arma::mat P_x_pred_out;
|
||||
arma::vec x_est;
|
||||
arma::mat P_x_est;
|
||||
};
|
||||
|
||||
#endif
|
@ -97,6 +97,7 @@
|
||||
#include "ishort_to_cshort.h"
|
||||
#include "labsat_signal_source.h"
|
||||
#include "mmse_resampler_conditioner.h"
|
||||
#include "multichannel_file_signal_source.h"
|
||||
#include "notch_filter.h"
|
||||
#include "notch_filter_lite.h"
|
||||
#include "nsr_file_signal_source.h"
|
||||
@ -1261,6 +1262,21 @@ std::unique_ptr<GNSSBlockInterface> GNSSBlockFactory::GetBlock(
|
||||
block = std::move(block_);
|
||||
}
|
||||
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
std::cout << "GNSS-SDR program ended." << std::endl;
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
else if (implementation == "Multichannel_File_Signal_Source")
|
||||
{
|
||||
try
|
||||
{
|
||||
std::unique_ptr<GNSSBlockInterface> block_(new MultichannelFileSignalSource(configuration.get(), role, in_streams,
|
||||
out_streams, queue));
|
||||
block = std::move(block_);
|
||||
}
|
||||
|
||||
catch (const std::exception& e)
|
||||
{
|
||||
std::cout << "GNSS-SDR program ended." << std::endl;
|
||||
|
@ -215,10 +215,10 @@ void GNSSFlowgraph::connect()
|
||||
}
|
||||
|
||||
DLOG(INFO) << "blocks connected internally";
|
||||
// Signal Source (i) > Signal conditioner (i) >
|
||||
// Signal Source (i) > Signal conditioner (i) >
|
||||
#ifndef ENABLE_FPGA
|
||||
int RF_Channels = 0;
|
||||
int signal_conditioner_ID = 0;
|
||||
unsigned int signal_conditioner_ID = 0;
|
||||
for (int i = 0; i < sources_count_; i++)
|
||||
{
|
||||
try
|
||||
@ -249,11 +249,14 @@ void GNSSFlowgraph::connect()
|
||||
DLOG(INFO) << "sig_source_.at(i)->get_right_block()->output_signature()->max_streams()=" << sig_source_.at(i)->get_right_block()->output_signature()->max_streams();
|
||||
DLOG(INFO) << "sig_conditioner_.at(signal_conditioner_ID)->get_left_block()->input_signature()=" << sig_conditioner_.at(signal_conditioner_ID)->get_left_block()->input_signature()->max_streams();
|
||||
|
||||
if (sig_source_.at(i)->get_right_block()->output_signature()->max_streams() > 1)
|
||||
if (sig_source_.at(i)->get_right_block()->output_signature()->max_streams() > 1 or sig_source_.at(i)->get_right_block()->output_signature()->max_streams() == -1)
|
||||
{
|
||||
if (sig_conditioner_.size() > signal_conditioner_ID)
|
||||
{
|
||||
LOG(INFO) << "connecting sig_source_ " << i << " stream " << j << " to conditioner " << j;
|
||||
top_block_->connect(sig_source_.at(i)->get_right_block(), j, sig_conditioner_.at(signal_conditioner_ID)->get_left_block(), 0);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (j == 0)
|
||||
@ -819,7 +822,7 @@ void GNSSFlowgraph::disconnect()
|
||||
|
||||
for (int j = 0; j < RF_Channels; j++)
|
||||
{
|
||||
if (sig_source_.at(i)->get_right_block()->output_signature()->max_streams() > 1)
|
||||
if (sig_source_.at(i)->get_right_block()->output_signature()->max_streams() > 1 or sig_source_.at(i)->get_right_block()->output_signature()->max_streams() == -1)
|
||||
{
|
||||
top_block_->disconnect(sig_source_.at(i)->get_right_block(), j, sig_conditioner_.at(signal_conditioner_ID)->get_left_block(), 0);
|
||||
}
|
||||
|
@ -21,6 +21,9 @@ add_executable(gnss-sdr ${CMAKE_CURRENT_SOURCE_DIR}/main.cc)
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(gnss-sdr PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(gnss-sdr PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(gnss-sdr PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(gnss-sdr PRIVATE Boost::filesystem Boost::system)
|
||||
|
@ -46,14 +46,6 @@
|
||||
#include <boost/exception/diagnostic_information.hpp> // for diagnostic_informatio
|
||||
#include <boost/exception/exception.hpp> // for exception
|
||||
#include <boost/thread/exceptions.hpp> // for thread_resource_error
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
#endif
|
||||
#include <gflags/gflags.h> // for ShutDownCommandLineFlags
|
||||
#include <glog/logging.h> // for FLAGS_log_dir
|
||||
#include <chrono> // for time_point
|
||||
@ -68,9 +60,20 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
namespace fs = std::filesystem;
|
||||
#include <system_error>
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem/operations.hpp> // for create_directories, exists
|
||||
#include <boost/filesystem/path.hpp> // for path, operator<<
|
||||
#include <boost/filesystem/path_traits.hpp> // for filesystem
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
@ -161,6 +161,11 @@ if(ENABLE_FPGA)
|
||||
add_definitions(-DFPGA_BLOCKS_TEST=1)
|
||||
endif()
|
||||
|
||||
if(ARMADILLO_VERSION_STRING VERSION_GREATER 8.400)
|
||||
# mvnrnd() requires 8.400
|
||||
add_definitions(-DARMADILLO_HAVE_MVNRND=1)
|
||||
endif()
|
||||
|
||||
find_package(Gnuplot)
|
||||
if(GNUPLOT_FOUND)
|
||||
add_definitions(-DGNUPLOT_EXECUTABLE="${GNUPLOT_EXECUTABLE}")
|
||||
@ -356,6 +361,9 @@ if(ENABLE_UNIT_TESTING)
|
||||
add_executable(run_tests ${CMAKE_CURRENT_SOURCE_DIR}/test_main.cc)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(run_tests PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(run_tests PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(run_tests PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(run_tests PRIVATE Boost::filesystem Boost::system)
|
||||
@ -447,6 +455,9 @@ if(ENABLE_FPGA)
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(gps_l1_ca_dll_pll_tracking_test_fpga PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(gps_l1_ca_dll_pll_tracking_test_fpga PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(gps_l1_ca_dll_pll_tracking_test_fpga PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(gps_l1_ca_dll_pll_tracking_test_fpga PRIVATE Boost::filesystem Boost::system)
|
||||
@ -492,6 +503,9 @@ function(add_system_test executable)
|
||||
add_executable(${executable} ${SYSTEM_TEST_SOURCES})
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(${executable} PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(${executable} PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(${executable} PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(${executable} PRIVATE Boost::filesystem Boost::system)
|
||||
@ -585,6 +599,9 @@ if(NOT ENABLE_PACKAGING AND NOT ENABLE_FPGA)
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(flowgraph_test PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(flowgraph_test PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(flowgraph_test PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(flowgraph_test PRIVATE Boost::filesystem Boost::system)
|
||||
@ -634,6 +651,9 @@ if(NOT ENABLE_PACKAGING AND NOT ENABLE_FPGA)
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(gnss_block_test PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(gnss_block_test PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(gnss_block_test PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(gnss_block_test PRIVATE Boost::filesystem Boost::system)
|
||||
@ -681,6 +701,9 @@ if(NOT ENABLE_PACKAGING AND NOT ENABLE_FPGA)
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(gnuradio_block_test PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(gnuradio_block_test PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(gnuradio_block_test PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(gnuradio_block_test PRIVATE Boost::filesystem Boost::system)
|
||||
@ -775,15 +798,26 @@ endif()
|
||||
|
||||
#########################################################
|
||||
if(NOT ENABLE_PACKAGING AND NOT ENABLE_FPGA)
|
||||
set(NONLINEAR_SOURCES "")
|
||||
if(ARMADILLO_VERSION_STRING VERSION_GREATER 8.400)
|
||||
set(NONLINEAR_SOURCES
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/unit-tests/signal-processing-blocks/tracking/cubature_filter_test.cc
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/unit-tests/signal-processing-blocks/tracking/unscented_filter_test.cc
|
||||
)
|
||||
endif()
|
||||
add_executable(trk_test
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/single_test_main.cc
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/unit-tests/signal-processing-blocks/tracking/galileo_e1_dll_pll_veml_tracking_test.cc
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/unit-tests/signal-processing-blocks/tracking/tracking_loop_filter_test.cc
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/unit-tests/signal-processing-blocks/tracking/cpu_multicorrelator_real_codes_test.cc
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/unit-tests/signal-processing-blocks/tracking/bayesian_estimation_test.cc
|
||||
${NONLINEAR_SOURCES}
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(trk_test PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(trk_test PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(trk_test PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(trk_test PRIVATE Boost::filesystem Boost::system)
|
||||
@ -825,6 +859,9 @@ if(NOT ENABLE_PACKAGING AND NOT ENABLE_FPGA)
|
||||
)
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(control_thread_test PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(control_thread_test PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(control_thread_test PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(control_thread_test PRIVATE Boost::filesystem Boost::system)
|
||||
|
@ -99,6 +99,10 @@ DECLARE_string(log_dir);
|
||||
#endif
|
||||
|
||||
#include "unit-tests/signal-processing-blocks/tracking/bayesian_estimation_test.cc"
|
||||
#if ARMADILLO_HAVE_MVNRND
|
||||
#include "unit-tests/signal-processing-blocks/tracking/cubature_filter_test.cc"
|
||||
#include "unit-tests/signal-processing-blocks/tracking/unscented_filter_test.cc"
|
||||
#endif
|
||||
#include "unit-tests/signal-processing-blocks/tracking/cpu_multicorrelator_real_codes_test.cc"
|
||||
#include "unit-tests/signal-processing-blocks/tracking/cpu_multicorrelator_test.cc"
|
||||
#include "unit-tests/signal-processing-blocks/tracking/galileo_e1_dll_pll_veml_tracking_test.cc"
|
||||
|
@ -38,8 +38,13 @@
|
||||
#include <random>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -55,17 +55,23 @@
|
||||
#include <utility>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#include <filesystem>
|
||||
#include <system_error>
|
||||
namespace fs = std::filesystem;
|
||||
namespace errorlib = std;
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
#include <boost/system/error_code.hpp>
|
||||
#include <boost/system/error_code.hpp> // for error_code
|
||||
namespace fs = boost::filesystem;
|
||||
namespace errorlib = boost::system;
|
||||
#endif
|
||||
|
||||
|
||||
DEFINE_string(config_file_ptest, std::string(""), "File containing alternative configuration parameters for the acquisition performance test.");
|
||||
DEFINE_string(acq_test_input_file, std::string(""), "File containing raw signal data, must be in int8_t format. The signal generator will not be used.");
|
||||
DEFINE_string(acq_test_implementation, std::string("GPS_L1_CA_PCPS_Acquisition"), "Acquisition block implementation under test. Alternatives: GPS_L1_CA_PCPS_Acquisition, GPS_L1_CA_PCPS_Acquisition_Fine_Doppler, Galileo_E1_PCPS_Ambiguous_Acquisition, GLONASS_L1_CA_PCPS_Acquisition, GLONASS_L2_CA_PCPS_Acquisition, GPS_L2_M_PCPS_Acquisition, Galileo_E5a_Pcps_Acquisition, GPS_L5i_PCPS_Acquisition");
|
||||
|
@ -59,8 +59,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -59,8 +59,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -60,13 +60,19 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
#endif
|
||||
|
||||
|
||||
// ######## GNURADIO BLOCK MESSAGE RECEVER #########
|
||||
class GalileoE1PcpsAmbiguousAcquisitionTest_msg_rx;
|
||||
|
||||
|
@ -59,8 +59,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -60,8 +60,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -1,7 +1,7 @@
|
||||
/*!
|
||||
* \file bayesian_estimation_positivity_test.cc
|
||||
* \brief This file implements timing tests for the Bayesian covariance estimator
|
||||
* \author Gerald LaMountain, 20168. gerald(at)ece.neu.edu
|
||||
* \file bayesian_estimation_test.cc
|
||||
* \brief This file implements feasability test for the BCE library.
|
||||
* \author Gerald LaMountain, 2018. gerald(at)ece.neu.edu
|
||||
*
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
|
@ -0,0 +1,162 @@
|
||||
/*!
|
||||
* \file cubature_filter_test.cc
|
||||
* \brief This file implements numerical accuracy test for the CKF library.
|
||||
* \author Gerald LaMountain, 2019. gerald(at)ece.neu.edu
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (C) 2010-2019 (see AUTHORS file for a list of contributors)
|
||||
*
|
||||
* GNSS-SDR is a software defined Global Navigation
|
||||
* Satellite Systems receiver
|
||||
*
|
||||
* This file is part of GNSS-SDR.
|
||||
*
|
||||
* GNSS-SDR is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNSS-SDR is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include "nonlinear_tracking.h"
|
||||
#include <armadillo>
|
||||
#include <gtest/gtest.h>
|
||||
#include <random>
|
||||
|
||||
#define CUBATURE_TEST_N_TRIALS 1000
|
||||
#define CUBATURE_TEST_TOLERANCE 0.01
|
||||
|
||||
class TransitionModel : public ModelFunction
|
||||
{
|
||||
public:
|
||||
TransitionModel(const arma::mat& kf_F) { coeff_mat = kf_F; };
|
||||
virtual arma::vec operator()(const arma::vec& input) { return coeff_mat * input; };
|
||||
|
||||
private:
|
||||
arma::mat coeff_mat;
|
||||
};
|
||||
|
||||
class MeasurementModel : public ModelFunction
|
||||
{
|
||||
public:
|
||||
MeasurementModel(const arma::mat& kf_H) { coeff_mat = kf_H; };
|
||||
virtual arma::vec operator()(const arma::vec& input) { return coeff_mat * input; };
|
||||
|
||||
private:
|
||||
arma::mat coeff_mat;
|
||||
};
|
||||
|
||||
TEST(CubatureFilterComputationTest, CubatureFilterTest)
|
||||
{
|
||||
CubatureFilter kf_cubature;
|
||||
|
||||
arma::vec kf_x;
|
||||
arma::mat kf_P_x;
|
||||
|
||||
arma::vec kf_x_pre;
|
||||
arma::mat kf_P_x_pre;
|
||||
|
||||
arma::vec ckf_x_pre;
|
||||
arma::mat ckf_P_x_pre;
|
||||
|
||||
arma::vec kf_x_post;
|
||||
arma::mat kf_P_x_post;
|
||||
|
||||
arma::vec ckf_x_post;
|
||||
arma::mat ckf_P_x_post;
|
||||
|
||||
arma::mat kf_F;
|
||||
arma::mat kf_H;
|
||||
|
||||
arma::mat kf_Q;
|
||||
arma::mat kf_R;
|
||||
|
||||
arma::vec eta;
|
||||
arma::vec nu;
|
||||
|
||||
arma::vec kf_y;
|
||||
arma::mat kf_P_y;
|
||||
arma::mat kf_K;
|
||||
|
||||
ModelFunction* transition_function;
|
||||
ModelFunction* measurement_function;
|
||||
|
||||
//--- Perform initializations ------------------------------
|
||||
|
||||
std::random_device r;
|
||||
std::default_random_engine e1(r());
|
||||
std::normal_distribution<float> normal_dist(0, 5);
|
||||
std::uniform_real_distribution<float> uniform_dist(0.1, 5.0);
|
||||
std::uniform_int_distribution<> uniform_dist_int(1, 5);
|
||||
|
||||
uint8_t nx = 0;
|
||||
uint8_t ny = 0;
|
||||
|
||||
for (uint16_t k = 0; k < CUBATURE_TEST_N_TRIALS; k++)
|
||||
{
|
||||
nx = static_cast<uint8_t>(uniform_dist_int(e1));
|
||||
ny = static_cast<uint8_t>(uniform_dist_int(e1));
|
||||
|
||||
kf_x = arma::randn<arma::vec>(nx, 1);
|
||||
|
||||
kf_P_x_post = 5.0 * arma::diagmat(arma::randu<arma::vec>(nx, 1));
|
||||
kf_x_post = arma::mvnrnd(kf_x, kf_P_x_post);
|
||||
|
||||
kf_cubature.initialize(kf_x_post, kf_P_x_post);
|
||||
|
||||
// Prediction Step
|
||||
kf_F = arma::randu<arma::mat>(nx, nx);
|
||||
kf_Q = arma::diagmat(arma::randu<arma::vec>(nx, 1));
|
||||
|
||||
transition_function = new TransitionModel(kf_F);
|
||||
arma::mat ttx = (*transition_function)(kf_x_post);
|
||||
|
||||
kf_cubature.predict_sequential(kf_x_post, kf_P_x_post, transition_function, kf_Q);
|
||||
|
||||
ckf_x_pre = kf_cubature.get_x_pred();
|
||||
ckf_P_x_pre = kf_cubature.get_P_x_pred();
|
||||
|
||||
kf_x_pre = kf_F * kf_x_post;
|
||||
kf_P_x_pre = kf_F * kf_P_x_post * kf_F.t() + kf_Q;
|
||||
|
||||
EXPECT_TRUE(arma::approx_equal(ckf_x_pre, kf_x_pre, "absdiff", CUBATURE_TEST_TOLERANCE));
|
||||
EXPECT_TRUE(arma::approx_equal(ckf_P_x_pre, kf_P_x_pre, "absdiff", CUBATURE_TEST_TOLERANCE));
|
||||
|
||||
// Update Step
|
||||
kf_H = arma::randu<arma::mat>(ny, nx);
|
||||
kf_R = arma::diagmat(arma::randu<arma::vec>(ny, 1));
|
||||
|
||||
eta = arma::mvnrnd(arma::zeros<arma::vec>(nx, 1), kf_Q);
|
||||
nu = arma::mvnrnd(arma::zeros<arma::vec>(ny, 1), kf_R);
|
||||
|
||||
kf_y = kf_H * (kf_F * kf_x + eta) + nu;
|
||||
|
||||
measurement_function = new MeasurementModel(kf_H);
|
||||
kf_cubature.update_sequential(kf_y, kf_x_pre, kf_P_x_pre, measurement_function, kf_R);
|
||||
|
||||
ckf_x_post = kf_cubature.get_x_est();
|
||||
ckf_P_x_post = kf_cubature.get_P_x_est();
|
||||
|
||||
kf_P_y = kf_H * kf_P_x_pre * kf_H.t() + kf_R;
|
||||
kf_K = (kf_P_x_pre * kf_H.t()) * arma::inv(kf_P_y);
|
||||
|
||||
kf_x_post = kf_x_pre + kf_K * (kf_y - kf_H * kf_x_pre);
|
||||
kf_P_x_post = (arma::eye(nx, nx) - kf_K * kf_H) * kf_P_x_pre;
|
||||
|
||||
EXPECT_TRUE(arma::approx_equal(ckf_x_post, kf_x_post, "absdiff", CUBATURE_TEST_TOLERANCE));
|
||||
EXPECT_TRUE(arma::approx_equal(ckf_P_x_post, kf_P_x_post, "absdiff", CUBATURE_TEST_TOLERANCE));
|
||||
|
||||
delete transition_function;
|
||||
delete measurement_function;
|
||||
}
|
||||
}
|
@ -61,8 +61,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -60,8 +60,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -76,8 +76,13 @@
|
||||
#endif
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -60,8 +60,13 @@
|
||||
#include <vector>
|
||||
|
||||
#if HAS_STD_FILESYSTEM
|
||||
#if HAS_STD_FILESYSTEM_EXPERIMENTAL
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
#else
|
||||
#include <filesystem>
|
||||
namespace fs = std::filesystem;
|
||||
#endif
|
||||
#else
|
||||
#include <boost/filesystem.hpp>
|
||||
namespace fs = boost::filesystem;
|
||||
|
@ -0,0 +1,162 @@
|
||||
/*!
|
||||
* \file unscented_filter_test.cc
|
||||
* \brief This file implements numerical accuracy test for the CKF library.
|
||||
* \author Gerald LaMountain, 2019. gerald(at)ece.neu.edu
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*
|
||||
* Copyright (C) 2010-2019 (see AUTHORS file for a list of contributors)
|
||||
*
|
||||
* GNSS-SDR is a software defined Global Navigation
|
||||
* Satellite Systems receiver
|
||||
*
|
||||
* This file is part of GNSS-SDR.
|
||||
*
|
||||
* GNSS-SDR is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNSS-SDR is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||
*
|
||||
* -------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#include "nonlinear_tracking.h"
|
||||
#include <armadillo>
|
||||
#include <gtest/gtest.h>
|
||||
#include <random>
|
||||
|
||||
#define UNSCENTED_TEST_N_TRIALS 10
|
||||
#define UNSCENTED_TEST_TOLERANCE 10
|
||||
|
||||
class TransitionModelUKF : public ModelFunction
|
||||
{
|
||||
public:
|
||||
TransitionModelUKF(const arma::mat& kf_F) { coeff_mat = kf_F; };
|
||||
virtual arma::vec operator()(const arma::vec& input) { return coeff_mat * input; };
|
||||
|
||||
private:
|
||||
arma::mat coeff_mat;
|
||||
};
|
||||
|
||||
class MeasurementModelUKF : public ModelFunction
|
||||
{
|
||||
public:
|
||||
MeasurementModelUKF(const arma::mat& kf_H) { coeff_mat = kf_H; };
|
||||
virtual arma::vec operator()(const arma::vec& input) { return coeff_mat * input; };
|
||||
|
||||
private:
|
||||
arma::mat coeff_mat;
|
||||
};
|
||||
|
||||
TEST(UnscentedFilterComputationTest, UnscentedFilterTest)
|
||||
{
|
||||
UnscentedFilter kf_unscented;
|
||||
|
||||
arma::vec kf_x;
|
||||
arma::mat kf_P_x;
|
||||
|
||||
arma::vec kf_x_pre;
|
||||
arma::mat kf_P_x_pre;
|
||||
|
||||
arma::vec ukf_x_pre;
|
||||
arma::mat ukf_P_x_pre;
|
||||
|
||||
arma::vec kf_x_post;
|
||||
arma::mat kf_P_x_post;
|
||||
|
||||
arma::vec ukf_x_post;
|
||||
arma::mat ukf_P_x_post;
|
||||
|
||||
arma::mat kf_F;
|
||||
arma::mat kf_H;
|
||||
|
||||
arma::mat kf_Q;
|
||||
arma::mat kf_R;
|
||||
|
||||
arma::vec eta;
|
||||
arma::vec nu;
|
||||
|
||||
arma::vec kf_y;
|
||||
arma::mat kf_P_y;
|
||||
arma::mat kf_K;
|
||||
|
||||
ModelFunction* transition_function;
|
||||
ModelFunction* measurement_function;
|
||||
|
||||
//--- Perform initializations ------------------------------
|
||||
|
||||
std::random_device r;
|
||||
std::default_random_engine e1(r());
|
||||
std::normal_distribution<float> normal_dist(0, 5);
|
||||
std::uniform_real_distribution<float> uniform_dist(0.1, 5.0);
|
||||
std::uniform_int_distribution<> uniform_dist_int(1, 5);
|
||||
|
||||
uint8_t nx = 0;
|
||||
uint8_t ny = 0;
|
||||
|
||||
for (uint16_t k = 0; k < UNSCENTED_TEST_N_TRIALS; k++)
|
||||
{
|
||||
nx = static_cast<uint8_t>(uniform_dist_int(e1));
|
||||
ny = static_cast<uint8_t>(uniform_dist_int(e1));
|
||||
|
||||
kf_x = arma::randn<arma::vec>(nx, 1);
|
||||
|
||||
kf_P_x_post = 5.0 * arma::diagmat(arma::randu<arma::vec>(nx, 1));
|
||||
kf_x_post = arma::mvnrnd(kf_x, kf_P_x_post);
|
||||
|
||||
kf_unscented.initialize(kf_x_post, kf_P_x_post);
|
||||
|
||||
// Prediction Step
|
||||
kf_F = arma::randu<arma::mat>(nx, nx);
|
||||
kf_Q = arma::diagmat(arma::randu<arma::vec>(nx, 1));
|
||||
|
||||
transition_function = new TransitionModelUKF(kf_F);
|
||||
arma::mat ttx = (*transition_function)(kf_x_post);
|
||||
|
||||
kf_unscented.predict_sequential(kf_x_post, kf_P_x_post, transition_function, kf_Q);
|
||||
|
||||
ukf_x_pre = kf_unscented.get_x_pred();
|
||||
ukf_P_x_pre = kf_unscented.get_P_x_pred();
|
||||
|
||||
kf_x_pre = kf_F * kf_x_post;
|
||||
kf_P_x_pre = kf_F * kf_P_x_post * kf_F.t() + kf_Q;
|
||||
|
||||
EXPECT_TRUE(arma::approx_equal(ukf_x_pre, kf_x_pre, "absdiff", UNSCENTED_TEST_TOLERANCE));
|
||||
EXPECT_TRUE(arma::approx_equal(ukf_P_x_pre, kf_P_x_pre, "absdiff", UNSCENTED_TEST_TOLERANCE));
|
||||
|
||||
// Update Step
|
||||
kf_H = arma::randu<arma::mat>(ny, nx);
|
||||
kf_R = arma::diagmat(arma::randu<arma::vec>(ny, 1));
|
||||
|
||||
eta = arma::mvnrnd(arma::zeros<arma::vec>(nx, 1), kf_Q);
|
||||
nu = arma::mvnrnd(arma::zeros<arma::vec>(ny, 1), kf_R);
|
||||
|
||||
kf_y = kf_H * (kf_F * kf_x + eta) + nu;
|
||||
|
||||
measurement_function = new MeasurementModelUKF(kf_H);
|
||||
kf_unscented.update_sequential(kf_y, kf_x_pre, kf_P_x_pre, measurement_function, kf_R);
|
||||
|
||||
ukf_x_post = kf_unscented.get_x_est();
|
||||
ukf_P_x_post = kf_unscented.get_P_x_est();
|
||||
|
||||
kf_P_y = kf_H * kf_P_x_pre * kf_H.t() + kf_R;
|
||||
kf_K = (kf_P_x_pre * kf_H.t()) * arma::inv(kf_P_y);
|
||||
|
||||
kf_x_post = kf_x_pre + kf_K * (kf_y - kf_H * kf_x_pre);
|
||||
kf_P_x_post = (arma::eye(nx, nx) - kf_K * kf_H) * kf_P_x_pre;
|
||||
|
||||
EXPECT_TRUE(arma::approx_equal(ukf_x_post, kf_x_post, "absdiff", UNSCENTED_TEST_TOLERANCE));
|
||||
EXPECT_TRUE(arma::approx_equal(ukf_P_x_post, kf_P_x_post, "absdiff", UNSCENTED_TEST_TOLERANCE));
|
||||
|
||||
delete transition_function;
|
||||
delete measurement_function;
|
||||
}
|
||||
}
|
@ -58,6 +58,9 @@ add_executable(front-end-cal ${CMAKE_CURRENT_SOURCE_DIR}/main.cc)
|
||||
|
||||
if(${FILESYSTEM_FOUND})
|
||||
target_compile_definitions(front-end-cal PRIVATE -DHAS_STD_FILESYSTEM=1)
|
||||
if(${find_experimental})
|
||||
target_compile_definitions(front-end-cal PRIVATE -DHAS_STD_FILESYSTEM_EXPERIMENTAL=1)
|
||||
endif()
|
||||
target_link_libraries(front-end-cal PRIVATE std::filesystem)
|
||||
else()
|
||||
target_link_libraries(front-end-cal PRIVATE Boost::filesystem Boost::system)
|
||||
|
@ -99,3 +99,5 @@ else()
|
||||
message(STATUS "Boost Iostreams library not found.")
|
||||
message(STATUS " rinex2assist will not be built.")
|
||||
endif()
|
||||
|
||||
set(Boost_FOUND TRUE) # trick for summary report
|
||||
|
Loading…
x
Reference in New Issue
Block a user