Compare commits
No commits in common. "master" and "v1.0" have entirely different histories.
18
.astylerc
18
.astylerc
|
@ -1,18 +0,0 @@
|
|||
# gr-satnogs astyle parameters
|
||||
--errors-to-stdout
|
||||
--lineend=linux
|
||||
--preserve-date
|
||||
--suffix=none
|
||||
--style=stroustrup
|
||||
--convert-tabs
|
||||
--indent=spaces=2
|
||||
--align-pointer=name
|
||||
--align-reference=name
|
||||
--pad-header
|
||||
--add-braces
|
||||
--unpad-paren
|
||||
--pad-oper
|
||||
--pad-comma
|
||||
--convert-tabs
|
||||
--max-code-length=80
|
||||
|
|
@ -8,5 +8,4 @@ apps/*.py
|
|||
.cproject
|
||||
.pyproject
|
||||
.pydevproject
|
||||
nbproject/
|
||||
.vscode
|
||||
nbproject/
|
136
.gitlab-ci.yml
136
.gitlab-ci.yml
|
@ -1,136 +0,0 @@
|
|||
variables:
|
||||
GITLAB_CI_IMAGE_DEBIAN: 'debian:buster'
|
||||
stages:
|
||||
- style
|
||||
- test
|
||||
- build
|
||||
- deploy
|
||||
style:
|
||||
image: ${GITLAB_CI_IMAGE_DEBIAN}
|
||||
stage: style
|
||||
before_script:
|
||||
- apt-get update -qq
|
||||
- apt-get install -qq -y astyle
|
||||
script:
|
||||
- 'astyle --dry-run --options=.astylerc --formatted lib/*.cc lib/*.h include/satnogs/*.h | sed ''s/^Formatted/ERROR: Unformatted/;T;q1'''
|
||||
test:
|
||||
image: ${GITLAB_CI_IMAGE_DEBIAN}
|
||||
stage: test
|
||||
before_script:
|
||||
- apt-get update -qq
|
||||
- apt-get install -qq -y gnupg libcurl4
|
||||
- echo 'deb http://download.opensuse.org/repositories/home:/librespace:/satnogs-unstable/Debian_10/ /' > /etc/apt/sources.list.d/home:librespace:satnogs-unstable.list
|
||||
- apt-key adv --fetch-keys https://download.opensuse.org/repositories/home:librespace:satnogs-unstable/Debian_10/Release.key
|
||||
- apt-get update -qq -y
|
||||
- >
|
||||
apt-get install -q -y
|
||||
build-essential
|
||||
cmake
|
||||
doxygen
|
||||
git
|
||||
gnuradio-dev
|
||||
gr-soapy
|
||||
libboost-date-time-dev
|
||||
libboost-dev
|
||||
libboost-filesystem-dev
|
||||
libboost-program-options-dev
|
||||
libboost-regex-dev
|
||||
libboost-system-dev
|
||||
libboost-test-dev
|
||||
libboost-thread-dev
|
||||
libjsoncpp-dev
|
||||
liborc-0.4-dev
|
||||
libpng++-dev
|
||||
libvorbis-dev
|
||||
pkg-config
|
||||
python3-dev
|
||||
python3-six
|
||||
swig
|
||||
script:
|
||||
- mkdir -p build
|
||||
- cd build
|
||||
- cmake -DCMAKE_BUILD_TYPE=RelWithDebInfo -DCMAKE_INSTALL_PREFIX=/usr ..
|
||||
- make
|
||||
- make CTEST_OUTPUT_ON_FAILURE=1 test
|
||||
- make install
|
||||
- ldconfig
|
||||
- python3 -c "import satnogs"
|
||||
- rm -rf *
|
||||
- cmake -DCMAKE_BUILD_TYPE=RelWithDebInfo -DINCLUDE_DEBUG_BLOCKS=OFF -DCMAKE_INSTALL_PREFIX=/usr ..
|
||||
- make
|
||||
- make CTEST_OUTPUT_ON_FAILURE=1 test
|
||||
- make install
|
||||
- ldconfig
|
||||
- python3 -c "import satnogs"
|
||||
debian:
|
||||
stage: build
|
||||
image: ${GITLAB_CI_IMAGE_DEBIAN}
|
||||
before_script:
|
||||
- apt-get update -qq
|
||||
- apt-get install -qq -y gnupg libcurl4
|
||||
- echo 'deb http://download.opensuse.org/repositories/home:/librespace:/satnogs-unstable/Debian_10/ /' > /etc/apt/sources.list.d/home:librespace:satnogs-unstable.list
|
||||
- apt-key adv --fetch-keys https://download.opensuse.org/repositories/home:librespace:satnogs-unstable/Debian_10/Release.key
|
||||
- apt-get update
|
||||
- apt-get install -y devscripts git-buildpackage
|
||||
script:
|
||||
- mk-build-deps -i -r -t "apt-get -o Debug::pkgProblemResolver=yes --no-install-recommends -y"
|
||||
- PACKAGE_VERSION="$CI_COMMIT_TAG"
|
||||
- PACKAGE_VERSION="${PACKAGE_VERSION:-$(git describe --abbrev=8 2>/dev/null | tr '-' '+' | cut -c '2-' || true)}"
|
||||
- PACKAGE_VERSION="${PACKAGE_VERSION#v}"
|
||||
- |
|
||||
[ -z "$PACKAGE_VERSION" ] || {
|
||||
dch -b -M -v "${PACKAGE_VERSION}-1" "Bump to version '${PACKAGE_VERSION}-1'"
|
||||
dch -r -m ""
|
||||
}
|
||||
- |
|
||||
[ -n "$CI_COMMIT_TAG" ] || sed -i '/0001-remove-git-maint-version.patch/ d' debian/patches/series
|
||||
- gbp buildpackage -us -uc --git-upstream-tag='HEAD' --git-ignore-branch --git-ignore-new
|
||||
- mkdir artifacts
|
||||
- cp -a ../*.{deb,debian.tar.xz,dsc,build,buildinfo,changes,orig.tar.gz} artifacts/
|
||||
artifacts:
|
||||
expire_in: 1 week
|
||||
when: always
|
||||
paths:
|
||||
- artifacts
|
||||
deploy:
|
||||
stage: deploy
|
||||
image: ${GITLAB_CI_IMAGE_DEBIAN}
|
||||
before_script:
|
||||
- apt-get update
|
||||
- apt-get install -y osc
|
||||
script:
|
||||
- |
|
||||
cat <<-EOF > ~/.oscrc
|
||||
[general]
|
||||
apiurl = https://api.opensuse.org
|
||||
[https://api.opensuse.org]
|
||||
user = $OBS_USER
|
||||
pass = $OBS_PASS
|
||||
EOF
|
||||
- |
|
||||
PROJECT="${CI_COMMIT_TAG:+home:librespace:satnogs}"
|
||||
PROJECT="${PROJECT:-home:librespace:satnogs-unstable}"
|
||||
BASE_DIR="$(pwd)"
|
||||
OSC_WORKDIR="$BASE_DIR/osc_workdir"
|
||||
ARTIFACTS_DIR="$BASE_DIR/artifacts"
|
||||
DSC_FILENAME=$(basename $(ls "$ARTIFACTS_DIR"/*.dsc))
|
||||
PACKAGE="${CI_COMMIT_TAG:+${DSC_FILENAME%.dsc}}"
|
||||
PACKAGE="${PACKAGE:-${DSC_FILENAME%%_*}}"
|
||||
mkdir -p "$OSC_WORKDIR"
|
||||
cd "$OSC_WORKDIR"
|
||||
[ -d "$PROJECT" ] || osc co "$PROJECT"
|
||||
cd "$PROJECT"
|
||||
[ -d "$PACKAGE" ] || osc mkpac "$PACKAGE"
|
||||
rm -f "$PACKAGE"/*.{dsc,debian.tar.xz,orig.tar.gz}
|
||||
cp -a "$ARTIFACTS_DIR"/*.{dsc,debian.tar.xz,orig.tar.gz} "$PACKAGE"
|
||||
osc addremove -r
|
||||
osc ci -m "$DSC_FILENAME"
|
||||
cd "$BASE_DIR"
|
||||
rm -r "$OSC_WORKDIR"
|
||||
only:
|
||||
refs:
|
||||
- master
|
||||
- tags
|
||||
variables:
|
||||
- $OBS_USER
|
||||
- $OBS_PASS
|
160
CMakeLists.txt
160
CMakeLists.txt
|
@ -1,7 +1,6 @@
|
|||
# Copyright 2011,2012,2014,2016,2018 Free Software Foundation, Inc.
|
||||
# Copyright 2011,2012,2014 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-satnogs
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
@ -21,96 +20,70 @@
|
|||
########################################################################
|
||||
# Project setup
|
||||
########################################################################
|
||||
cmake_minimum_required(VERSION 3.8)
|
||||
include(GNUInstallDirs)
|
||||
cmake_minimum_required(VERSION 3.1 FATAL_ERROR)
|
||||
project(gr-satnogs CXX C)
|
||||
enable_testing()
|
||||
|
||||
# Install to PyBOMBS target prefix if defined
|
||||
if(DEFINED ENV{PYBOMBS_PREFIX})
|
||||
set(CMAKE_INSTALL_PREFIX $ENV{PYBOMBS_PREFIX})
|
||||
message(STATUS "PyBOMBS installed GNU Radio. Setting CMAKE_INSTALL_PREFIX to $ENV{PYBOMBS_PREFIX}")
|
||||
endif()
|
||||
# Enable C++11 support
|
||||
set (CMAKE_CXX_STANDARD 11)
|
||||
add_definitions(-std=c++11)
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wextra")
|
||||
|
||||
# Select the release build type by default to get optimization flags
|
||||
#select the release build type by default to get optimization flags
|
||||
if(NOT CMAKE_BUILD_TYPE)
|
||||
set(CMAKE_BUILD_TYPE "Release")
|
||||
message(STATUS "Build type not specified: defaulting to release.")
|
||||
endif(NOT CMAKE_BUILD_TYPE)
|
||||
set(CMAKE_BUILD_TYPE ${CMAKE_BUILD_TYPE} CACHE STRING "")
|
||||
|
||||
# Make sure our local CMake Modules path comes first
|
||||
#make sure our local CMake Modules path comes first
|
||||
list(INSERT CMAKE_MODULE_PATH 0 ${CMAKE_SOURCE_DIR}/cmake/Modules)
|
||||
|
||||
# Set the version information here
|
||||
set(VERSION_MAJOR 1)
|
||||
set(VERSION_API 5)
|
||||
set(VERSION_ABI 1)
|
||||
set(VERSION_PATCH git)
|
||||
|
||||
cmake_policy(SET CMP0011 NEW)
|
||||
|
||||
# Enable generation of compile_commands.json for code completion engines
|
||||
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||
|
||||
########################################################################
|
||||
# Compiler specific setup
|
||||
########################################################################
|
||||
if((CMAKE_CXX_COMPILER_ID MATCHES "Clang" OR
|
||||
CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
|
||||
AND NOT WIN32)
|
||||
if(CMAKE_COMPILER_IS_GNUCXX AND NOT WIN32)
|
||||
#http://gcc.gnu.org/wiki/Visibility
|
||||
add_definitions(-fvisibility=hidden)
|
||||
#false positives
|
||||
add_definitions(-Wno-format-overflow)
|
||||
endif()
|
||||
|
||||
if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
elseif(CMAKE_CXX_COMPILER_ID MATCHES "Clang")
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
elseif(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC")
|
||||
set(CMAKE_CXX_STANDARD 11)
|
||||
else()
|
||||
message(WARNING "C++ standard could not be set because compiler is not GNU, Clang or MSVC.")
|
||||
endif()
|
||||
|
||||
if(CMAKE_C_COMPILER_ID STREQUAL "GNU")
|
||||
set(CMAKE_C_STANDARD 11)
|
||||
elseif(CMAKE_C_COMPILER_ID MATCHES "Clang")
|
||||
set(CMAKE_C_STANDARD 11)
|
||||
elseif(CMAKE_C_COMPILER_ID STREQUAL "MSVC")
|
||||
set(CMAKE_C_STANDARD 11)
|
||||
else()
|
||||
message(WARNING "C standard could not be set because compiler is not GNU, Clang or MSVC.")
|
||||
endif()
|
||||
|
||||
########################################################################
|
||||
# Find gnuradio build dependencies
|
||||
# Find boost
|
||||
########################################################################
|
||||
find_package(PythonLibs 3)
|
||||
|
||||
find_package(Gnuradio "3.8" REQUIRED
|
||||
COMPONENTS runtime blocks fft analog filter digital pmt)
|
||||
include(GrVersion)
|
||||
|
||||
include(GrPlatform) #define LIB_SUFFIX
|
||||
|
||||
if(NOT CMAKE_MODULES_DIR)
|
||||
set(CMAKE_MODULES_DIR lib${LIB_SUFFIX}/cmake)
|
||||
endif(NOT CMAKE_MODULES_DIR)
|
||||
if(UNIX AND EXISTS "/usr/lib64")
|
||||
list(APPEND BOOST_LIBRARYDIR "/usr/lib64") #fedora 64-bit fix
|
||||
endif(UNIX AND EXISTS "/usr/lib64")
|
||||
set(Boost_ADDITIONAL_VERSIONS
|
||||
"1.35.0" "1.35" "1.36.0" "1.36" "1.37.0" "1.37" "1.38.0" "1.38" "1.39.0" "1.39"
|
||||
"1.40.0" "1.40" "1.41.0" "1.41" "1.42.0" "1.42" "1.43.0" "1.43" "1.44.0" "1.44"
|
||||
"1.45.0" "1.45" "1.46.0" "1.46" "1.47.0" "1.47" "1.48.0" "1.48" "1.49.0" "1.49"
|
||||
"1.50.0" "1.50" "1.51.0" "1.51" "1.52.0" "1.52" "1.53.0" "1.53" "1.54.0" "1.54"
|
||||
"1.55.0" "1.55" "1.56.0" "1.56" "1.57.0" "1.57" "1.58.0" "1.58" "1.59.0" "1.59"
|
||||
"1.60.0" "1.60" "1.61.0" "1.61" "1.62.0" "1.62" "1.63.0" "1.63" "1.64.0" "1.64"
|
||||
"1.65.0" "1.65" "1.66.0" "1.66" "1.67.0" "1.67" "1.68.0" "1.68" "1.69.0" "1.69"
|
||||
)
|
||||
find_package(Boost "1.35" COMPONENTS filesystem system)
|
||||
|
||||
if(NOT Boost_FOUND)
|
||||
message(FATAL_ERROR "Boost required to compile satnogs")
|
||||
endif()
|
||||
|
||||
########################################################################
|
||||
# Install directories
|
||||
########################################################################
|
||||
include(GrPlatform) #define LIB_SUFFIX
|
||||
set(GR_RUNTIME_DIR bin)
|
||||
set(GR_LIBRARY_DIR lib${LIB_SUFFIX})
|
||||
set(GR_INCLUDE_DIR include/satnogs)
|
||||
set(GR_CMAKE_DIR ${CMAKE_MODULES_DIR}/satnogs)
|
||||
set(GR_DATA_DIR share)
|
||||
set(GR_PKG_DATA_DIR ${GR_DATA_DIR}/${CMAKE_PROJECT_NAME})
|
||||
set(GR_DOC_DIR ${GR_DATA_DIR}/doc)
|
||||
set(GR_PKG_DOC_DIR ${GR_DOC_DIR}/${CMAKE_PROJECT_NAME})
|
||||
set(GR_CONF_DIR etc)
|
||||
set(GR_PKG_CONF_DIR ${GR_CONF_DIR}/${CMAKE_PROJECT_NAME}/conf.d)
|
||||
set(GR_LIBEXEC_DIR libexec)
|
||||
set(GR_PKG_LIBEXEC_DIR ${GR_LIBEXEC_DIR}/${CMAKE_PROJECT_NAME})
|
||||
|
||||
set(GRC_BLOCKS_DIR ${GR_PKG_DATA_DIR}/grc/blocks)
|
||||
|
||||
########################################################################
|
||||
# On Apple only, set install name and use rpath correctly, if not already set
|
||||
|
@ -133,27 +106,27 @@ if(APPLE)
|
|||
endif(APPLE)
|
||||
|
||||
########################################################################
|
||||
# Find gr-satnogs build dependencies
|
||||
# Find gnuradio build dependencies
|
||||
########################################################################
|
||||
find_package (Threads REQUIRED)
|
||||
|
||||
########################################################################
|
||||
# Find gnuradio build dependencies
|
||||
########################################################################
|
||||
find_package(CppUnit)
|
||||
find_package(Doxygen)
|
||||
find_package(SWIG REQUIRED)
|
||||
find_package(Volk REQUIRED)
|
||||
find_package(OggVorbis REQUIRED)
|
||||
find_package(PNG REQUIRED)
|
||||
find_package(png++ REQUIRED)
|
||||
find_package(JsonCpp REQUIRED)
|
||||
find_package(soapy)
|
||||
|
||||
if(NOT soapy_FOUND)
|
||||
message(WARNING "gr-soapy not found. Flowgraphs may not be able to execute!")
|
||||
# Search for GNU Radio and its components and versions. Add any
|
||||
# components required to the list of GR_REQUIRED_COMPONENTS (in all
|
||||
# caps such as FILTER or FFT) and change the version to the minimum
|
||||
# API compatible version required.
|
||||
set(GR_REQUIRED_COMPONENTS RUNTIME)
|
||||
find_package(Gnuradio "3.7.2" REQUIRED)
|
||||
|
||||
if(NOT CPPUNIT_FOUND)
|
||||
message(FATAL_ERROR "CppUnit required to compile satnogs")
|
||||
endif()
|
||||
|
||||
########################################################################
|
||||
# Include or not into the module blocks for debugging
|
||||
########################################################################
|
||||
option(INCLUDE_DEBUG_BLOCKS
|
||||
"Enable/Disable blocks that are used for debugging purposes" ON)
|
||||
|
||||
########################################################################
|
||||
# Setup doxygen option
|
||||
########################################################################
|
||||
|
@ -163,6 +136,29 @@ else(DOXYGEN_FOUND)
|
|||
option(ENABLE_DOXYGEN "Build docs using Doxygen" OFF)
|
||||
endif(DOXYGEN_FOUND)
|
||||
|
||||
########################################################################
|
||||
# Setup the include and linker paths
|
||||
########################################################################
|
||||
include_directories(
|
||||
${CMAKE_SOURCE_DIR}/lib
|
||||
${CMAKE_SOURCE_DIR}/include
|
||||
${CMAKE_BINARY_DIR}/lib
|
||||
${CMAKE_BINARY_DIR}/include
|
||||
${Boost_INCLUDE_DIRS}
|
||||
${CPPUNIT_INCLUDE_DIRS}
|
||||
${GNURADIO_ALL_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
link_directories(
|
||||
${Boost_LIBRARY_DIRS}
|
||||
${CPPUNIT_LIBRARY_DIRS}
|
||||
${GNURADIO_RUNTIME_LIBRARY_DIRS}
|
||||
)
|
||||
|
||||
# Set component parameters
|
||||
set(GR_SATNOGS_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR}/include CACHE INTERNAL "" FORCE)
|
||||
set(GR_SATNOGS_SWIG_INCLUDE_DIRS ${CMAKE_CURRENT_SOURCE_DIR}/swig CACHE INTERNAL "" FORCE)
|
||||
|
||||
########################################################################
|
||||
# Create uninstall target
|
||||
########################################################################
|
||||
|
@ -182,15 +178,17 @@ add_subdirectory(include/satnogs)
|
|||
add_subdirectory(lib)
|
||||
add_subdirectory(swig)
|
||||
add_subdirectory(python)
|
||||
if(ENABLE_GRC)
|
||||
add_subdirectory(grc)
|
||||
endif(ENABLE_GRC)
|
||||
add_subdirectory(grc)
|
||||
add_subdirectory(apps)
|
||||
add_subdirectory(docs)
|
||||
|
||||
########################################################################
|
||||
# Install cmake search helper for this library
|
||||
########################################################################
|
||||
if(NOT CMAKE_MODULES_DIR)
|
||||
set(CMAKE_MODULES_DIR lib${LIB_SUFFIX}/cmake)
|
||||
endif(NOT CMAKE_MODULES_DIR)
|
||||
|
||||
install(FILES cmake/Modules/satnogsConfig.cmake
|
||||
DESTINATION ${CMAKE_MODULES_DIR}/satnogs
|
||||
)
|
||||
|
|
|
@ -1,18 +0,0 @@
|
|||
# Maintainers
|
||||
* Manolis Surligas (surligas@gmail.com)
|
||||
* Pierros Papadeas (pierros@papadeas.gr)
|
||||
* Goerge Vardakis (vardakis@csd.uoc.gr)
|
||||
|
||||
# Package Mainteners
|
||||
* Vasilis Tsiligiannis (acinonyx@openwrt.gr)
|
||||
|
||||
# Contributors
|
||||
* Corey Shields (cshields@gmail.com)
|
||||
* LongHairedHacker(sebastian@sebastians-site.de)
|
||||
* Nikos Karamolegkos (nkaramolegos@csd.uoc.g)
|
||||
* Mark Jessop (vk5qi@rfhead.net)
|
||||
* Fabian P. Schmidt (kerel-fs@gmx.de)
|
||||
* Thanos Gkiolias (agiolias@csd.uoc.gr)
|
||||
* Patrick Dohmen (dl4pd@darc.de)
|
||||
* Kostis Triantayllakis (ctriant@csd.uoc.gr)
|
||||
* Alexander Jenke
|
348
README.md
348
README.md
|
@ -1,342 +1,34 @@
|
|||
# gr-satnogs: SatNOGS GNU Radio Out-Of-Tree Module
|
||||
![gr-satnogs](docs/assets/gr-satnogs.png)
|
||||
|
||||
gr-satnogs is an out-of-tree GNU Radio module that provides all the necessary tools
|
||||
for decoding signals from various scientific and academic satellites.
|
||||
It also provides blocks for debugging and experimenting with known satellite
|
||||
telecommunication schemes.
|
||||
for decoding signals from various scientific and academic sattelites.
|
||||
|
||||
## Installation
|
||||
## Install
|
||||
|
||||
### Requirements
|
||||
* GNU Radio ( > 3.8.0 )
|
||||
* CMake ( > 3.8)
|
||||
* G++ (> 4.8)
|
||||
* Boost
|
||||
* VOLK
|
||||
* libogg
|
||||
* libvorbis
|
||||
* libpng
|
||||
* libpng++
|
||||
* libjsoncpp
|
||||
* git
|
||||
* swig
|
||||
* gr-soapy (>= 2.0.0)
|
||||
1. GNU Radio ( > 3.7.2 )
|
||||
2. CMake ( > 3.1)
|
||||
3. G++ (with C++11 support)
|
||||
4. VOLK
|
||||
5. git
|
||||
6. gr-osmocom (optional, for using the flowgraphs)
|
||||
|
||||
**Optional**
|
||||
* [iqzip](https://gitlab.com/librespacefoundation/sdrmakerspace/iqzip) (for compresses IQ storage)
|
||||
### Installation
|
||||
|
||||
#### Debian / Ubuntu
|
||||
```bash
|
||||
sudo apt install -y
|
||||
libboost-dev \
|
||||
libboost-date-time-dev \
|
||||
libboost-filesystem-dev \
|
||||
libboost-program-options-dev \
|
||||
libboost-system-dev \
|
||||
libboost-thread-dev \
|
||||
libboost-regex-dev \
|
||||
libboost-test-dev \
|
||||
swig \
|
||||
cmake \
|
||||
build-essential \
|
||||
pkg-config \
|
||||
gnuradio-dev \
|
||||
libconfig++-dev \
|
||||
libgmp-dev \
|
||||
liborc-0.4-0 \
|
||||
liborc-0.4-dev \
|
||||
liborc-0.4-dev-bin \
|
||||
libjsoncpp-dev \
|
||||
libpng++-dev \
|
||||
libvorbis-dev \
|
||||
git
|
||||
```
|
||||
#### openSUSE
|
||||
```bash
|
||||
sudo zypper in -y \
|
||||
boost-devel \
|
||||
libboost_filesystem-devel \
|
||||
libboost_system-devel \
|
||||
libboost_thread-devel \
|
||||
libboost_program_options-devel \
|
||||
libboost_regex-devel \
|
||||
libboost_test-devel \
|
||||
python3 \
|
||||
python3-devel \
|
||||
swig \
|
||||
cmake \
|
||||
gcc-c++ \
|
||||
gcc \
|
||||
soapy-sdr \
|
||||
soapy-sdr-devel \
|
||||
gnuradio \
|
||||
gnuradio-devel \
|
||||
gmp-devel \
|
||||
libmpir-devel \
|
||||
liborc-0_4-0 \
|
||||
orc \
|
||||
log4cpp-devel \
|
||||
git
|
||||
```
|
||||
|
||||
### Installation from source
|
||||
|
||||
```bash
|
||||
git clone https://gitlab.com/librespacefoundation/satnogs/gr-satnogs.git
|
||||
cd gr-satnogs
|
||||
mkdir build
|
||||
cd build
|
||||
cmake ..
|
||||
make -j $(nproc --all)
|
||||
sudo make install
|
||||
```
|
||||
1. `git clone https://github.com/satnogs/gr-satnogs.git`
|
||||
2. `cd gr-satnogs`
|
||||
3. `mkdir build`
|
||||
4. `cmake ..`
|
||||
5. `make`
|
||||
6. `sudo make install`
|
||||
|
||||
If this is the first time you are building the gr-satnogs module run
|
||||
```bash
|
||||
sudo ldconfig
|
||||
```
|
||||
`sudo ldconfig`
|
||||
|
||||
#### Advanced
|
||||
By default, the **SatNOGS** module will use the default installation prefix.
|
||||
This highly depends on the Linux distribution. You can use the `CMAKE_INSTALL_PREFIX`
|
||||
variable to alter the default installation path.
|
||||
E.g:
|
||||
|
||||
```bash
|
||||
cmake -DCMAKE_INSTALL_PREFIX=/usr ..
|
||||
```
|
||||
|
||||
Also, by default the build system enables a set of blocks used for debugging
|
||||
during the development. The enable/disable switch is controlled through the
|
||||
`INCLUDE_DEBUG_BLOCKS` boolean variable. If for example, you want to disable the
|
||||
debugging blocks, the **CMake** command would be:
|
||||
|
||||
```bash
|
||||
cmake -DINCLUDE_DEBUG_BLOCKS=OFF ..
|
||||
```
|
||||
|
||||
Another common control option is the library suffix of the Linux distribution.
|
||||
There are distributions like Fedora, openSUSE, e.t.c that the their 64-bit version
|
||||
use the `lib64` folder to store the 64-bit versions of their dynamic libraries.
|
||||
On the other hand, distributions like Ubuntu do the exact opposite. They use
|
||||
`lib` directory for the libraries of the native architecture and place the 32-bit versions
|
||||
on the `lib32` directory. In any case the correct library directory suffix
|
||||
can be specified with the `LIB_SUFFIX` variable. For example:
|
||||
|
||||
```bash
|
||||
cmake -DLIB_SUFFIX=64 -DCMAKE_INSTALL_PREFIX=/usr -DINCLUDE_DEBUG_BLOCKS=OFF ..
|
||||
```
|
||||
|
||||
will install the libraries at the `/usr/lib64` directory.
|
||||
|
||||
## Development Guide
|
||||
The development is performed on the `master` branch.
|
||||
For special cases where a team of developers should work an a common feature,
|
||||
maintainers may add a special branch on the repository.
|
||||
However, it will be removed at the time it will be merged on the `master` branch.
|
||||
All developers should derive the `master` branch for their feature branches and merge
|
||||
requests should also issued at this branch.
|
||||
Developers should ensure that do **not** alter the CMake version tags in any
|
||||
way.
|
||||
It is a responsibility of the maintainers team.
|
||||
|
||||
Before submitting a new merge request, rebase the `master` branch and
|
||||
confirm that the automated CI tests have successfully completed for all platforms
|
||||
mandated by the `.gitlab-ci.yml` recipe.
|
||||
|
||||
### Coding style
|
||||
For the C++ code, `gr-satnogs` uses a slightly modified version of the
|
||||
**Stroustrup** style, which is a nicer adaptation of the well known K&R style.
|
||||
In addition, we decided to decrease the indentation from 4 to 2 spaces.
|
||||
This choice was made mainly to avoid braking statements with long namespaces.
|
||||
We also found ourselves, that with smaller indentation we use more descriptive
|
||||
variable names, avoiding frustrating abbreviations without phoenixes etc.
|
||||
|
||||
At the root directory of the project there is the `astyle` options
|
||||
file `.astylerc` containing the proper configuration.
|
||||
Developers can import this configuration to their favorite editor.
|
||||
In addition the `hooks/pre-commit` file contains a Git hook,
|
||||
that can be used to perform before every commit, code style formatting
|
||||
with `astyle` and the `.astylerc` parameters.
|
||||
To enable this hook developers should copy the hook at their `.git/hooks`
|
||||
directory.
|
||||
Failing to comply with the coding style described by the `.astylerc`
|
||||
will result to failure of the automated tests running on our CI services.
|
||||
So make sure that you either import on your editor the coding style rules
|
||||
or use the `pre-commit` Git hook.
|
||||
|
||||
|
||||
Regarding the naming of files and variables, we use the underscore naming
|
||||
convention (`do_this`) instead of camel cases (`DoNotDoThis`).
|
||||
Exception to this rule is the CMake module filenames. In addition,
|
||||
all private variables of a C++ class, should start with the prefix
|
||||
`d_` allowing the developers to spot easily private members of the object.
|
||||
|
||||
|
||||
### Adding a new Satellite Demodulator
|
||||
Demodulators are responsible for filtering, resampling and demodulating an
|
||||
analog signal and converting it into suitable form, for a decoder to be able
|
||||
to extract the frame and its data. In most cases this is a simple bit stream.
|
||||
|
||||
If the existing demodulators (FSK, AFSK, BPSK, DUV) do not meet
|
||||
the requirements of a satellite, you may submit your custom demodulator.
|
||||
Please make sure that you put the GNU Radio Companion files in the `apps/flowgraphs`
|
||||
directory.
|
||||
|
||||
### Adding a new Satellite Decoder
|
||||
With the new architecture, adding a new satellite has become an easy and straight
|
||||
forward task.
|
||||
The decoders are implemented using the following approach.
|
||||
|
||||
There is a generic block called `frame_decoder`.
|
||||
This block should not be altered at any case. If you find yourself in a situation
|
||||
that you need to apply modifications on this block, raise an issue on the
|
||||
[issue tracker](https://gitlab.com/librespacefoundation/satnogs/gr-satnogs/issues)
|
||||
The `frame_decoder` block accepts two parameters. A `satnogs::decoder`
|
||||
object and the item size of the input stream. Internally, the `frame_decoder`
|
||||
invokes the `decode()` method of the `satnogs::decoder` class.
|
||||
|
||||
The `satnogs::decoder` class, is a virtual class providing a generic API that
|
||||
every derived decoder class should implement.
|
||||
The core of this class is the
|
||||
|
||||
```cpp
|
||||
decoder_status_t
|
||||
decode(const void *in, int len)
|
||||
```
|
||||
method. This method accepts an input buffer `in`. The type of the items depends
|
||||
on the implementation. It also takes the `len` argument specifying the number
|
||||
of items available in the `in` buffer.
|
||||
The method returns a `decoder_status_t` class object.
|
||||
|
||||
```cpp
|
||||
class decoder_status
|
||||
{
|
||||
public:
|
||||
int consumed;
|
||||
bool decode_success;
|
||||
pmt::pmt_t data;
|
||||
|
||||
decoder_status () :
|
||||
consumed(0),
|
||||
decode_success(false),
|
||||
data(pmt::make_dict())
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
typedef class decoder_status decoder_status_t;
|
||||
```
|
||||
The class contains three fields that allow the `frame_decoder` block to operate
|
||||
continuously, without any further assistance. It is responsibility of the derived
|
||||
decoder class to properly set the values to these fields.
|
||||
|
||||
* The `consumed` class should contain the number of items consumed during the
|
||||
`decode()` method invocation. It is ok to consume 0, less than `len` or `len`
|
||||
items but not more.
|
||||
* `decode_success` should be set to true only if a frame was successfully
|
||||
decoded and its data are available on the `data` field.
|
||||
* `data` field is a `pmt::pmt_t` dictionary containing the decoded data and other
|
||||
information regarding it, using the `gr-satnogs` metadata format. More about them
|
||||
in the [Metadata](#metadata) section
|
||||
|
||||
|
||||
### Metadata
|
||||
Each decoder generates a `pmt::pmt_t` dictionary containing the decoded data and
|
||||
other information regarding the decoded frame.
|
||||
The `gr::satnogs::metadata` class provides a set of commonly used metadata
|
||||
keys.
|
||||
The table below describes some of them:
|
||||
|
||||
| Key | Description |
|
||||
| --- | ----------- |
|
||||
| pdu | This string field contains the decoded data in base64 form |
|
||||
| time | The time at which the frame was received. Time is represented in an ISO 8601 string with microsecond accuracy |
|
||||
| crc_valid | Boolean indicating if the CRC check has been successfully passed |
|
||||
| freq_offset | Float value indicating the frequency offset observed |
|
||||
| corrected_bits | `uint64_t` with the number of corrected bits |
|
||||
| symbol_erasures | `uint64_t` with the number of erased symbols |
|
||||
| sample_start | `uint64_t` with the sample index at which the decoder identified the start of the frame |
|
||||
| sample_cnt | `uint64_t` with the number of samples of a valid frame. `sample_start + sample_cnt` specify the sample index at the end of the frame |
|
||||
|
||||
The method `Json::Value
|
||||
metadata::to_json(const pmt::pmt_t& m)` is converts the dictionary `m`
|
||||
into a valid JSON object. There is also the `std::string
|
||||
metadata::keys()` static method which returns a list with the available
|
||||
metadata keys. This method is also available in Python through the Swig interface.
|
||||
For example:
|
||||
|
||||
```python
|
||||
$ python
|
||||
>>> import satnogs
|
||||
>>> satnogs.metadata.keys()
|
||||
'[pdu, crc_valid, freq_offset, corrected_bits, time, sample_start, sample_cnt, symbol_erasures]'
|
||||
>>>
|
||||
```
|
||||
|
||||
Using the `json_converter` block, developers can convert a `pmt::pmt_t`
|
||||
dictionary of a decoder into a `pmt::pmt_t` blob,
|
||||
containing the raw bytes of the JSON string, which then can be passed to a UDP
|
||||
sink targeting the `satnogs-client`.
|
||||
The `json_converter` block accepts also a string that may be used to inject
|
||||
an arbitrary number of additional information under the `extra` JSON field.
|
||||
Of course, this string should be in a JSON valid format.
|
||||
|
||||
For example, such a JSON string with information on the extra field could be like
|
||||
|
||||
```json
|
||||
{
|
||||
"corrected_bits" : 0,
|
||||
"extra" :
|
||||
{
|
||||
"x" : 3,
|
||||
"y" : "test"
|
||||
},
|
||||
"pdu" : "igAg7nRAOCAniUMAtIoAAAAAAAAAAAAAAABNJ4kfAFD4wwAfAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA==",
|
||||
"symbol_erasures" : 0,
|
||||
"time" : "2019-09-11T15:39:13.514138Z"
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
### Release Policy
|
||||
The `gr-satnogs` OOT module uses the `major.api-compatibility.minor`
|
||||
versioning scheme. is used by the
|
||||
[satnogs-client](https://gitlab.com/librespacefoundation/satnogs/satnogs-client),
|
||||
so the release and versioning policy is based on how the
|
||||
`satnogs-client` is affected by the changes on the `gr-satnogs` software.
|
||||
|
||||
* Minor changes, bug fixes or improvements that do not affect in anyway
|
||||
the `satnogs-client` advance the `minor` version.
|
||||
* The `api-compatibility` indicates changes that require modifications
|
||||
on `satnogs-client` but do not brake the backwards compatibility
|
||||
(e.g a new satellite decoder).
|
||||
In other words, the `satnogs-client` should continue to operate normally
|
||||
without any modifications. Changes on `satnogs-client` should be performed
|
||||
only to integrate the new features.
|
||||
* `major` version advances when the changes break backwards compatibility with
|
||||
the `satnogs-client`.
|
||||
|
||||
For every release change a tag with the corresponding version is created.
|
||||
Releases can be retrieved by the
|
||||
[tags](https://gitlab.com/librespacefoundation/satnogs/gr-satnogs/tags) page.
|
||||
|
||||
## Website and Contact
|
||||
For more information about SatNOGS please visit our [site](https://satnogs.org/)
|
||||
and our [community forums](https://community.libre.space).
|
||||
You can also chat with the SatNOGS community at
|
||||
[https://riot.im/app/#/room/#satnogs:matrix.org](https://riot.im/app/#/room/#satnogs:matrix.org),
|
||||
or on IRC at `#satnogs` on Freenode.
|
||||
For chatting around the development and for watching the changes in project's gitlab repositories,
|
||||
join in [https://riot.im/app/#/room/#satnogs-dev:matrix.org](https://riot.im/app/#/room/#satnogs-dev:matrix.org)
|
||||
or the IRC channel `#satnogs-dev` on Freenode.
|
||||
## Website
|
||||
For more indormation about SatNOGS please visit our [site](https://satnogs.org/).
|
||||
|
||||
## License
|
||||
|
||||
![SatNOGS](docs/assets/SatNOGS-logo-vertical-black.png)
|
||||
![Libre Space Foundation](docs/assets/LSF_HD_Horizontal_Color1-300x66.png)
|
||||
© 2016-2019 [Libre Space Foundation](https://libre.space).
|
||||
|
||||
Licensed under the [GPLv3](LICENSE).
|
||||
© 2016 [Libre Space Foundation](http://librespacefoundation.org).
|
||||
|
||||
Licensed under the [GPLv3](LICENSE).
|
|
@ -19,4 +19,8 @@
|
|||
|
||||
include(GrPython)
|
||||
|
||||
add_subdirectory(flowgraphs)
|
||||
GR_PYTHON_INSTALL(
|
||||
PROGRAMS
|
||||
flowgraphs/upsat_transceiver_cli.py
|
||||
DESTINATION bin
|
||||
)
|
||||
|
|
|
@ -1,48 +0,0 @@
|
|||
# Copyright 2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
add_subdirectory(satellites)
|
||||
|
||||
set(flowgraphs
|
||||
afsk1200_ax25.grc
|
||||
bpsk_ax25.grc
|
||||
cw_decoder.grc
|
||||
example_flowgraph.grc
|
||||
fsk_ax25.grc
|
||||
iq_receiver.grc
|
||||
)
|
||||
message(“Compiling GRC SatNOGS flowgraphs…”)
|
||||
foreach(grc_file ${flowgraphs})
|
||||
|
||||
message("Compiling " ${grc_file})
|
||||
execute_process(COMMAND grcc ${grc_file}
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
|
||||
)
|
||||
endforeach()
|
||||
|
||||
GR_PYTHON_INSTALL(
|
||||
PROGRAMS
|
||||
satnogs_afsk1200_ax25.py
|
||||
satnogs_bpsk_ax25.py
|
||||
satnogs_cw_decoder.py
|
||||
satnogs_example_flowgraph.py
|
||||
satnogs_fsk_ax25.py
|
||||
satnogs_iq_receiver.py
|
||||
DESTINATION bin
|
||||
)
|
|
@ -1,46 +0,0 @@
|
|||
# SatNOGS flowgraphs
|
||||
This directory contains all the available flowgraphs that can be executed from
|
||||
the `satnogs-client`.
|
||||
|
||||
## Contribution guide
|
||||
Flowgraphs are placed inside the `apps/flowgraphs` directory.
|
||||
If a decoding flowgraph targets only specific satellite/mission, the
|
||||
flowgraph should be placed inside the `apps/flowgraphs/satellites` directory.
|
||||
|
||||
Each flowgraph should have a representative name (eg `voyager_decoder`) and
|
||||
both the GNU Radio file (`.grc`) and the generated pythons script should be available.
|
||||
Python auto-generared flowgraph scripts should have the `satnogs_` prefix.
|
||||
This can be performed by setting properly the `ID` field of the `Options` block
|
||||
of the flowgraph.
|
||||
For example the `voyager_decoder.grc` should generate a python executable named
|
||||
`satnogs_voyager_decoder.py`
|
||||
|
||||
**NOTE:**: Custom python GNU Radio scripts are not allowed.
|
||||
Each flowgraph should be able to be generated from the corresponding `.grc` file.
|
||||
|
||||
All generated python scripts should be installed using the `CMake` build system.
|
||||
To do so, edit properly the `apps/CMakeLists.txt` or `apps/flowgraphs/satellites/CMakeLists.txt` file.
|
||||
|
||||
In the `apps/flowgraphs` directory, the is an example flowgraph called `example_flowgraph.grc`
|
||||
that can be used as a base.
|
||||
|
||||
### Execution arguements interface
|
||||
The `stanogs-client` and the `gr-satnogs` communicate through a set of
|
||||
predefined command line arguments.
|
||||
Depending the decoding flowgraph, additional arguments may exist or missing.
|
||||
However, there is a set of mandatory arguments.
|
||||
|
||||
* `--antenna`: The name of the antenna to use
|
||||
* `--dev-args`: SDR device specific arguments
|
||||
* `--bb-gain`: Baseband gain
|
||||
* `--if-gain`: Intermediate frequency gain
|
||||
* `--rf-gain`: RF gain
|
||||
* `--ppm`: The PPM correction
|
||||
* `--rx-freq`: RX frequency
|
||||
* `--rx-sdr-device`: The RX SDR device identification name (e.g uhd, airspy, etc)
|
||||
* `--rigctl-port`: The `rigctld` port
|
||||
* `--doppler-correction-per-sec`: Number of Doppler corrections per second
|
||||
* `--lo-offset`: Offset from the desired center frequency. The flowgraph should
|
||||
tune the SDR with this offset from the center frequency and digitally compensate it.
|
||||
This eliminate the problem of the DC leakage, expressed in the majority of the
|
||||
SDR devices.
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -1,936 +0,0 @@
|
|||
options:
|
||||
parameters:
|
||||
author: Manolis Surligas (surligas@gmail.com)
|
||||
category: Custom
|
||||
cmake_opt: ''
|
||||
comment: ''
|
||||
copyright: ''
|
||||
description: A CW (Morse) Decoder
|
||||
gen_cmake: 'On'
|
||||
gen_linking: dynamic
|
||||
generate_options: no_gui
|
||||
hier_block_src_path: '.:'
|
||||
id: satnogs_cw_decoder
|
||||
max_nouts: '0'
|
||||
output_language: python
|
||||
placement: (0,0)
|
||||
qt_qss_theme: ''
|
||||
realtime_scheduling: ''
|
||||
run: 'True'
|
||||
run_command: '{python} -u {filename}'
|
||||
run_options: run
|
||||
sizing_mode: fixed
|
||||
thread_safe_setters: ''
|
||||
title: CW Decoder
|
||||
window_size: 3000, 3000
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 8]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
blocks:
|
||||
- name: audio_samp_rate
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '48000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1240, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dec
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '8'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1456, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dot_samples
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: int((1.2 / wpm) / (1.0 / (audio_samp_rate / 10.0)))
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1360, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_agc2_xx_0
|
||||
id: analog_agc2_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
attack_rate: 1e-4
|
||||
comment: ''
|
||||
decay_rate: 1e-4
|
||||
gain: '1.0'
|
||||
max_gain: '65536'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
reference: '1.0'
|
||||
type: complex
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [280, 460.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_agc2_xx_0_0
|
||||
id: analog_agc2_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
attack_rate: '0.01'
|
||||
comment: ''
|
||||
decay_rate: '0.001'
|
||||
gain: '0.0'
|
||||
max_gain: '65536'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
reference: '0.015'
|
||||
type: complex
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [616, 348.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_pll_carriertracking_cc_0
|
||||
id: analog_pll_carriertracking_cc
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
max_freq: 2*math.pi*2500
|
||||
maxoutbuf: '0'
|
||||
min_freq: -2*math.pi*2500
|
||||
minoutbuf: '0'
|
||||
w: 2*math.pi/100
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [736, 476.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: antenna
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [880, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bfo_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bfo_freq shifts the carrier from 0 Hz to a
|
||||
|
||||
frequency that corresponds to the CW audio
|
||||
|
||||
tone. This tone is typically 1 kHz.'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 1e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1368, 76.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_complex_to_mag_0
|
||||
id: blocks_complex_to_mag
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1456, 616.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: blocks_complex_to_real_0
|
||||
id: blocks_complex_to_real
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1000, 384.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_delay_0
|
||||
id: blocks_delay
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
delay: int(dot_samples//dec)
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
num_ports: '1'
|
||||
type: complex
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1120, 540.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_keep_one_in_n_0
|
||||
id: blocks_keep_one_in_n
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: 'Decimate manually so we
|
||||
|
||||
can avoid an extra filter'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
n: '10'
|
||||
type: complex
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [592, 496.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: blocks_multiply_conjugate_cc_0
|
||||
id: blocks_multiply_conjugate_cc
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1256, 496.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_rotator_cc_0_0
|
||||
id: blocks_rotator_cc
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
phase_inc: 2.0 * math.pi * (bfo_freq / audio_samp_rate)
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [808, 380.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bw
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bandwidth should configure RF filters on some devices.
|
||||
|
||||
Set to 0.0 for automatic calculation.'
|
||||
hide: none
|
||||
label: Bandwidth
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1040, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decoded_data_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/.satnogs/data/data
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [0, 748.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dev_args
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device arguments
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [432, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: doppler_correction_per_sec
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [160, 748.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_iq_dump
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [256, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: test.wav
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [144, 668.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: fir_filter_xxx_0
|
||||
id: fir_filter_xxx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
decim: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_delay: '0'
|
||||
taps: '[1.0] * int(dot_samples//dec)'
|
||||
type: ccc
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1408, 500.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: gain
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [960, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: import_0
|
||||
id: import
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
imports: import satnogs
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [200, 20.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: import_1
|
||||
id: import
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
imports: import math
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [200, 68.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: iq_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/iq.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: lo_offset
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'To avoid the SDR carrier at the DC
|
||||
|
||||
we shift the LO a little further'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [800, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_0
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
cutoff_freq: '200'
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: audio_samp_rate/10
|
||||
type: fir_filter_ccf
|
||||
width: 0.1e3
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [936, 444.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_0_0
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
cutoff_freq: '3000'
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: audio_samp_rate
|
||||
type: fir_filter_ccf
|
||||
width: 1e3
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [432, 444.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rigctl_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '4532'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 748.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rx_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e6
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [720, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: samp_rate_rx
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device Sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [568, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_cw_to_symbol_1
|
||||
id: satnogs_cw_to_symbol
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
conf_level: '0.9'
|
||||
hysteresis: dot_samples//dec
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: audio_samp_rate/10
|
||||
threshold: '2.0'
|
||||
wpm: wpm
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1264, 596.0]
|
||||
rotation: 180
|
||||
state: true
|
||||
- name: satnogs_doppler_compensation_0
|
||||
id: satnogs_doppler_compensation
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
compensate: '1'
|
||||
lo_offset: lo_offset
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
out_samp_rate: audio_samp_rate
|
||||
samp_rate: samp_rate_rx
|
||||
sat_freq: rx_freq
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [560, 140.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: satnogs_frame_file_sink_0_0
|
||||
id: satnogs_frame_file_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
output_type: '0'
|
||||
prefix_name: decoded_data_file_path
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [832, 620.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_iq_sink_0
|
||||
id: satnogs_iq_sink
|
||||
parameters:
|
||||
activate: enable_iq_dump
|
||||
affinity: ''
|
||||
alias: ''
|
||||
append: 'False'
|
||||
comment: ''
|
||||
filename: iq_file_path
|
||||
scale: '16768'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [40, 548.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_morse_decoder_0
|
||||
id: satnogs_morse_decoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
min_frame_len: '3'
|
||||
minoutbuf: '0'
|
||||
unrecognized_char: ord('#')
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1064, 620.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_ogg_encoder_0
|
||||
id: satnogs_ogg_encoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
filename: file_path
|
||||
quality: '1.0'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1144, 364.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_tcp_rigctl_msg_source_0
|
||||
id: satnogs_tcp_rigctl_msg_source
|
||||
parameters:
|
||||
addr: '"127.0.0.1"'
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
interval: int(1000.0/doppler_correction_per_sec) + 1
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mode: 'False'
|
||||
mtu: '1500'
|
||||
port: rigctl_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [304, 252.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_udp_msg_sink_0_0
|
||||
id: satnogs_udp_msg_sink
|
||||
parameters:
|
||||
addr: udp_IP
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
mtu: '1500'
|
||||
port: udp_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [832, 692.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_waterfall_sink_0
|
||||
id: satnogs_waterfall_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
center_freq: rx_freq
|
||||
comment: ''
|
||||
fft_size: '1024'
|
||||
filename: waterfall_file_path
|
||||
mode: '1'
|
||||
rps: '10'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [40, 356.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: soapy_rx_device
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: driver=invalid
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [304, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_source_0
|
||||
id: soapy_source
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amp_gain0: '0'
|
||||
ant0: antenna
|
||||
ant1: RX2
|
||||
args: dev_args
|
||||
balance0: '0'
|
||||
balance1: '0'
|
||||
bw0: bw
|
||||
bw1: '0'
|
||||
center_freq0: rx_freq - lo_offset
|
||||
center_freq1: '0'
|
||||
clock_rate: '0'
|
||||
clock_source: ''
|
||||
comment: ''
|
||||
correction0: '0'
|
||||
correction1: '0'
|
||||
dc_offset0: '0'
|
||||
dc_offset1: '0'
|
||||
dc_offset_auto_mode0: 'False'
|
||||
dc_offset_auto_mode1: 'False'
|
||||
dev: soapy_rx_device
|
||||
devname: custom
|
||||
gain_auto_mode0: 'False'
|
||||
gain_auto_mode1: 'False'
|
||||
ifgr_gain: '59'
|
||||
lna_gain0: '10'
|
||||
lna_gain1: '10'
|
||||
manual_gain0: 'False'
|
||||
manual_gain1: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mix_gain0: '10'
|
||||
mix_gain1: '10'
|
||||
nchan: '1'
|
||||
nco_freq0: '0'
|
||||
nco_freq1: '0'
|
||||
overall_gain0: gain
|
||||
overall_gain1: '10'
|
||||
pga_gain0: '24'
|
||||
pga_gain1: '24'
|
||||
rfgr_gain: '9'
|
||||
samp_rate: samp_rate_rx
|
||||
sdrplay_agc_setpoint: '-30'
|
||||
sdrplay_biastee: 'True'
|
||||
sdrplay_dabnotch: 'False'
|
||||
sdrplay_if_mode: Zero-IF
|
||||
sdrplay_rfnotch: 'False'
|
||||
tia_gain0: '0'
|
||||
tia_gain1: '0'
|
||||
tuner_gain0: '10'
|
||||
tuner_gain1: '10'
|
||||
type: fc32
|
||||
vga_gain0: '10'
|
||||
vga_gain1: '10'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [304, 116.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: udp_IP
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: 127.0.0.1
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [496, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: udp_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '16887'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [496, 748.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: virtual_sink_0
|
||||
id: virtual_sink
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [864, 172.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: virtual_source_0
|
||||
id: virtual_source
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [40, 492.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: waterfall_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/waterfall.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [0, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: wpm
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1168, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
connections:
|
||||
- [analog_agc2_xx_0, '0', low_pass_filter_0_0, '0']
|
||||
- [analog_agc2_xx_0_0, '0', blocks_rotator_cc_0_0, '0']
|
||||
- [analog_pll_carriertracking_cc_0, '0', low_pass_filter_0, '0']
|
||||
- [blocks_complex_to_mag_0, '0', satnogs_cw_to_symbol_1, '0']
|
||||
- [blocks_complex_to_real_0, '0', satnogs_ogg_encoder_0, '0']
|
||||
- [blocks_delay_0, '0', blocks_multiply_conjugate_cc_0, '1']
|
||||
- [blocks_keep_one_in_n_0, '0', analog_pll_carriertracking_cc_0, '0']
|
||||
- [blocks_multiply_conjugate_cc_0, '0', fir_filter_xxx_0, '0']
|
||||
- [blocks_rotator_cc_0_0, '0', blocks_complex_to_real_0, '0']
|
||||
- [fir_filter_xxx_0, '0', blocks_complex_to_mag_0, '0']
|
||||
- [low_pass_filter_0, '0', blocks_delay_0, '0']
|
||||
- [low_pass_filter_0, '0', blocks_multiply_conjugate_cc_0, '0']
|
||||
- [low_pass_filter_0_0, '0', analog_agc2_xx_0_0, '0']
|
||||
- [low_pass_filter_0_0, '0', blocks_keep_one_in_n_0, '0']
|
||||
- [satnogs_cw_to_symbol_1, out, satnogs_morse_decoder_0, in]
|
||||
- [satnogs_doppler_compensation_0, '0', virtual_sink_0, '0']
|
||||
- [satnogs_morse_decoder_0, out, satnogs_frame_file_sink_0_0, frame]
|
||||
- [satnogs_morse_decoder_0, out, satnogs_udp_msg_sink_0_0, in]
|
||||
- [satnogs_tcp_rigctl_msg_source_0, freq, satnogs_doppler_compensation_0, doppler]
|
||||
- [soapy_source_0, '0', satnogs_doppler_compensation_0, '0']
|
||||
- [virtual_source_0, '0', analog_agc2_xx_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_iq_sink_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_waterfall_sink_0, '0']
|
||||
|
||||
metadata:
|
||||
file_format: 1
|
|
@ -1,634 +0,0 @@
|
|||
options:
|
||||
parameters:
|
||||
author: Manolis Surligas (surligas@gmail.com)
|
||||
category: Custom
|
||||
cmake_opt: ''
|
||||
comment: ''
|
||||
copyright: ''
|
||||
description: An example flowgraph that can be used as a base for decoding flowgraphs
|
||||
gen_cmake: 'On'
|
||||
gen_linking: dynamic
|
||||
generate_options: no_gui
|
||||
hier_block_src_path: '.:'
|
||||
id: satnogs_example_flowgraph
|
||||
max_nouts: '0'
|
||||
output_language: python
|
||||
placement: (0,0)
|
||||
qt_qss_theme: ''
|
||||
realtime_scheduling: ''
|
||||
run: 'True'
|
||||
run_command: '{python} -u {filename}'
|
||||
run_options: run
|
||||
sizing_mode: fixed
|
||||
thread_safe_setters: ''
|
||||
title: An example flowgraph
|
||||
window_size: 3000, 3000
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 8]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
blocks:
|
||||
- name: audio_samp_rate
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '48000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1704, 52]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: audio_samp_rate_0
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '48000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1320, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decimation
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: satnogs.find_decimation(baudrate, 2, audio_samp_rate)
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1120, 44.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: filter_rate
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '250000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1704, 260]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: xlate_filter_taps
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: firdes.low_pass(1, samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76)
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1704, 164]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_quadrature_demod_cf_0_0_0
|
||||
id: analog_quadrature_demod_cf
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain: '0.9'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [976, 308.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: antenna
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [848, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: baudrate
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '9600.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1232, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bw
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bandwidth should configure RF filters on some devices.
|
||||
|
||||
Set to 0.0 for automatic calculation.'
|
||||
hide: none
|
||||
label: Bandwidth
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1008, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dc_blocker_xx_0_0
|
||||
id: dc_blocker_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
length: '1024'
|
||||
long_form: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
type: ff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1144, 300.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decoded_data_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/.satnogs/data/data
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dev_args_0
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device arguments
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: doppler_correction_per_sec
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [176, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_iq_dump
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [272, 588.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: test.wav
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [160, 588.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: gain
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [928, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: iq_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/iq.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [416, 588.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: lo_offset
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'To avoid the SDR carrier at the DC
|
||||
|
||||
we shift the LO a little further'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [768, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rigctl_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '4532'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [416, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rx_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e6
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [688, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: samp_rate_rx
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device Sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [536, 44.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_doppler_compensation_0
|
||||
id: satnogs_doppler_compensation
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
compensate: '1'
|
||||
lo_offset: lo_offset
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
out_samp_rate: audio_samp_rate
|
||||
samp_rate: samp_rate_rx
|
||||
sat_freq: rx_freq
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [528, 164.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: satnogs_iq_sink_0
|
||||
id: satnogs_iq_sink
|
||||
parameters:
|
||||
activate: enable_iq_dump
|
||||
affinity: ''
|
||||
alias: ''
|
||||
append: 'False'
|
||||
comment: ''
|
||||
filename: iq_file_path
|
||||
scale: '16768'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [976, 500.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_ogg_encoder_0
|
||||
id: satnogs_ogg_encoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
filename: file_path
|
||||
quality: '1.0'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1288, 292.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_tcp_rigctl_msg_source_0
|
||||
id: satnogs_tcp_rigctl_msg_source
|
||||
parameters:
|
||||
addr: '"127.0.0.1"'
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
interval: int(1000.0/doppler_correction_per_sec) + 1
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mode: 'False'
|
||||
mtu: '1500'
|
||||
port: rigctl_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [272, 276.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_waterfall_sink_0
|
||||
id: satnogs_waterfall_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
center_freq: rx_freq
|
||||
comment: ''
|
||||
fft_size: '1024'
|
||||
filename: waterfall_file_path
|
||||
mode: '1'
|
||||
rps: '10'
|
||||
samp_rate: baudrate*decimation
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [976, 364.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_rx_device
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: driver=invalid
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [272, 36.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_source_0
|
||||
id: soapy_source
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amp_gain0: '0'
|
||||
ant0: antenna
|
||||
ant1: RX2
|
||||
args: dev_args
|
||||
balance0: '0'
|
||||
balance1: '0'
|
||||
bw0: bw
|
||||
bw1: '0'
|
||||
center_freq0: rx_freq - lo_offset
|
||||
center_freq1: '0'
|
||||
clock_rate: '0'
|
||||
clock_source: ''
|
||||
comment: ''
|
||||
correction0: '0'
|
||||
correction1: '0'
|
||||
dc_offset0: '0'
|
||||
dc_offset1: '0'
|
||||
dc_offset_auto_mode0: 'False'
|
||||
dc_offset_auto_mode1: 'False'
|
||||
dev: soapy_rx_device
|
||||
devname: custom
|
||||
gain_auto_mode0: 'False'
|
||||
gain_auto_mode1: 'False'
|
||||
ifgr_gain: '59'
|
||||
lna_gain0: '10'
|
||||
lna_gain1: '10'
|
||||
manual_gain0: 'False'
|
||||
manual_gain1: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mix_gain0: '10'
|
||||
mix_gain1: '10'
|
||||
nchan: '1'
|
||||
nco_freq0: '0'
|
||||
nco_freq1: '0'
|
||||
overall_gain0: gain
|
||||
overall_gain1: '10'
|
||||
pga_gain0: '24'
|
||||
pga_gain1: '24'
|
||||
rfgr_gain: '9'
|
||||
samp_rate: samp_rate_rx
|
||||
sdrplay_agc_setpoint: '-30'
|
||||
sdrplay_biastee: 'True'
|
||||
sdrplay_dabnotch: 'False'
|
||||
sdrplay_if_mode: Zero-IF
|
||||
sdrplay_rfnotch: 'False'
|
||||
tia_gain0: '0'
|
||||
tia_gain1: '0'
|
||||
tuner_gain0: '10'
|
||||
tuner_gain1: '10'
|
||||
type: fc32
|
||||
vga_gain0: '10'
|
||||
vga_gain1: '10'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [272, 140.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: udp_IP
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: 127.0.0.1
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [512, 588.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: udp_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '16887'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [512, 668.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: virtual_sink_0
|
||||
id: virtual_sink
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [816, 196.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: virtual_source_0
|
||||
id: virtual_source
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [624, 404.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: waterfall_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/waterfall.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 588.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
connections:
|
||||
- [analog_quadrature_demod_cf_0_0_0, '0', dc_blocker_xx_0_0, '0']
|
||||
- [dc_blocker_xx_0_0, '0', satnogs_ogg_encoder_0, '0']
|
||||
- [satnogs_doppler_compensation_0, '0', virtual_sink_0, '0']
|
||||
- [satnogs_tcp_rigctl_msg_source_0, freq, satnogs_doppler_compensation_0, doppler]
|
||||
- [soapy_source_0, '0', satnogs_doppler_compensation_0, '0']
|
||||
- [virtual_source_0, '0', analog_quadrature_demod_cf_0_0_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_iq_sink_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_waterfall_sink_0, '0']
|
||||
|
||||
metadata:
|
||||
file_format: 1
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -1,473 +0,0 @@
|
|||
options:
|
||||
parameters:
|
||||
author: Manolis Surligas (surligas@gmail.com)
|
||||
category: '[GRC Hier Blocks]'
|
||||
cmake_opt: ''
|
||||
comment: ''
|
||||
copyright: ''
|
||||
description: Generic IQ receiver with arbitrary output sampling rate
|
||||
gen_cmake: 'On'
|
||||
gen_linking: dynamic
|
||||
generate_options: no_gui
|
||||
hier_block_src_path: '.:'
|
||||
id: satnogs_iq_receiver
|
||||
max_nouts: '0'
|
||||
output_language: python
|
||||
placement: (0,0)
|
||||
qt_qss_theme: ''
|
||||
realtime_scheduling: ''
|
||||
run: 'True'
|
||||
run_command: '{python} -u {filename}'
|
||||
run_options: run
|
||||
sizing_mode: fixed
|
||||
thread_safe_setters: ''
|
||||
title: satnogs_iq_receiver
|
||||
window_size: 2*1080,1080
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 4.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
blocks:
|
||||
- name: antenna
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [968, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bw
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bandwidth should configure RF filters on some devices.
|
||||
|
||||
Set to 0.0 for automatic calculation.'
|
||||
hide: none
|
||||
label: Bandwidth
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1120, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dev_args
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device arguments
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [520, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: doppler_correction_per_sec
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 548.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_doppler_correction
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [176, 548.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_iq_dump
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [256, 468.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: test.wav
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [160, 468.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: gain
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1048, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: import_0
|
||||
id: import
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
imports: import math
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 164.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: iq_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/iq.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [384, 468.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: lo_offset
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'To avoid the SDR carrier at the DC
|
||||
|
||||
we shift the LO a little further'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [888, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: out_samp_rate
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Output sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1392, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rigctl_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '4532'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [384, 548.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rx_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e6
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [808, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: samp_rate_rx
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device Sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [656, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_doppler_compensation_0
|
||||
id: satnogs_doppler_compensation
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
compensate: enable_doppler_correction
|
||||
lo_offset: lo_offset
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
out_samp_rate: out_samp_rate
|
||||
samp_rate: samp_rate_rx
|
||||
sat_freq: rx_freq
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [656, 220.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: satnogs_iq_sink_0
|
||||
id: satnogs_iq_sink
|
||||
parameters:
|
||||
activate: enable_iq_dump
|
||||
affinity: ''
|
||||
alias: ''
|
||||
append: 'False'
|
||||
comment: ''
|
||||
filename: iq_file_path
|
||||
scale: '16768'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1104, 340.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_tcp_rigctl_msg_source_0
|
||||
id: satnogs_tcp_rigctl_msg_source
|
||||
parameters:
|
||||
addr: '"127.0.0.1"'
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
interval: int(1000.0/doppler_correction_per_sec) + 1
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mode: 'False'
|
||||
mtu: '1500'
|
||||
port: rigctl_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 332.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_waterfall_sink_0
|
||||
id: satnogs_waterfall_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
center_freq: rx_freq
|
||||
comment: ''
|
||||
fft_size: '1024'
|
||||
filename: waterfall_file_path
|
||||
mode: '1'
|
||||
rps: '10'
|
||||
samp_rate: out_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1104, 212.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_rx_device
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: driver=invalid
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_source_0
|
||||
id: soapy_source
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amp_gain0: '0'
|
||||
ant0: antenna
|
||||
ant1: RX2
|
||||
args: dev_args
|
||||
balance0: '0'
|
||||
balance1: '0'
|
||||
bw0: bw
|
||||
bw1: '0'
|
||||
center_freq0: rx_freq - lo_offset
|
||||
center_freq1: '0'
|
||||
clock_rate: '0'
|
||||
clock_source: ''
|
||||
comment: ''
|
||||
correction0: '0'
|
||||
correction1: '0'
|
||||
dc_offset0: '0'
|
||||
dc_offset1: '0'
|
||||
dc_offset_auto_mode0: 'False'
|
||||
dc_offset_auto_mode1: 'False'
|
||||
dev: soapy_rx_device
|
||||
devname: custom
|
||||
gain_auto_mode0: 'False'
|
||||
gain_auto_mode1: 'False'
|
||||
ifgr_gain: '59'
|
||||
lna_gain0: '10'
|
||||
lna_gain1: '10'
|
||||
manual_gain0: 'False'
|
||||
manual_gain1: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mix_gain0: '10'
|
||||
mix_gain1: '10'
|
||||
nchan: '1'
|
||||
nco_freq0: '0'
|
||||
nco_freq1: '0'
|
||||
overall_gain0: gain
|
||||
overall_gain1: '10'
|
||||
pga_gain0: '24'
|
||||
pga_gain1: '24'
|
||||
rfgr_gain: '9'
|
||||
samp_rate: samp_rate_rx
|
||||
sdrplay_agc_setpoint: '-30'
|
||||
sdrplay_biastee: 'True'
|
||||
sdrplay_dabnotch: 'False'
|
||||
sdrplay_if_mode: Zero-IF
|
||||
sdrplay_rfnotch: 'False'
|
||||
tia_gain0: '0'
|
||||
tia_gain1: '0'
|
||||
tuner_gain0: '10'
|
||||
tuner_gain1: '10'
|
||||
type: fc32
|
||||
vga_gain0: '10'
|
||||
vga_gain1: '10'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 196.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: waterfall_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/waterfall.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 468.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
connections:
|
||||
- [satnogs_doppler_compensation_0, '0', satnogs_iq_sink_0, '0']
|
||||
- [satnogs_doppler_compensation_0, '0', satnogs_waterfall_sink_0, '0']
|
||||
- [satnogs_tcp_rigctl_msg_source_0, freq, satnogs_doppler_compensation_0, doppler]
|
||||
- [soapy_source_0, '0', satnogs_doppler_compensation_0, '0']
|
||||
|
||||
metadata:
|
||||
file_format: 1
|
|
@ -1,35 +0,0 @@
|
|||
### SatNOGS NOAA APT Decoder
|
||||
|
||||
`--antenna`: Specify the RX antenna of SDR device
|
||||
|
||||
`--bb-gain`: Specify the baseband (BB )gain of the SDR device
|
||||
|
||||
`--dev-args`: Set device specific arguments
|
||||
|
||||
`--doppler-correction-per-sec`: Doppler corrections per second
|
||||
|
||||
`--file-path`: File path of the output audio file
|
||||
|
||||
`--if-gain`: Specify the intermediate frequency (IF) gain of the SDR device
|
||||
|
||||
`--image-file-path`: File path of the output image file(s)
|
||||
|
||||
`--lo-offset`: Local oscillator offset
|
||||
|
||||
`--ppm`: Set PPM
|
||||
|
||||
`--rf-gain`: Specify the radio frequency (RF) gain of the SDR device
|
||||
|
||||
`--rigctl-port`: Specify the listening port of the rigctl daemon (rigctld)
|
||||
|
||||
`--rx-freq`: Set the target frequency of the satellite
|
||||
|
||||
`--rx-sdr-device`: Specify the RX SDR device. Possible values: ['usrpb200','usrp2','rtlsdr','airspy','hackrf']
|
||||
|
||||
`--waterfall-file-path`: File path of the output waterfall data file
|
||||
|
||||
`--split-images`: Split the two images contained in the received image. Use 1 for Yes, 0 for No
|
||||
|
||||
`--sync`: Synchronize image to the APT training sequence. Use 1 for Yes, 0 for No
|
||||
|
||||
`--flip-images`: Rotate images 180 degrees. Use 1 for Yes, 0 for No
|
|
@ -1,811 +0,0 @@
|
|||
options:
|
||||
parameters:
|
||||
author: Thanos Giolias (agiolias@csd.uoc.gr), Nikos Karamolegos (karamolegkos.n@gmail.com),
|
||||
Manolis Surligas (surligas@gmail.com)
|
||||
category: Custom
|
||||
cmake_opt: ''
|
||||
comment: ''
|
||||
copyright: ''
|
||||
description: A DUV Decoder for the AMSAT FOX satellites
|
||||
gen_cmake: 'On'
|
||||
gen_linking: dynamic
|
||||
generate_options: no_gui
|
||||
hier_block_src_path: '.:'
|
||||
id: satnogs_amsat_fox_duv_decoder
|
||||
max_nouts: '0'
|
||||
output_language: python
|
||||
placement: (0,0)
|
||||
qt_qss_theme: ''
|
||||
realtime_scheduling: ''
|
||||
run: 'True'
|
||||
run_command: '{python} -u {filename}'
|
||||
run_options: run
|
||||
sizing_mode: fixed
|
||||
thread_safe_setters: ''
|
||||
title: AMSAT FOX DUV Decoder
|
||||
window_size: 3000, 3000
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 8]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
blocks:
|
||||
- name: audio_samp_rate
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '48000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1056, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: deviation
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '5000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [616, 836.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: max_modulation_freq
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '3000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [616, 772.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: variable_amsat_duv_decoder_0
|
||||
id: variable_amsat_duv_decoder
|
||||
parameters:
|
||||
comment: ''
|
||||
control_symbol: '0011111010'
|
||||
frame_len: '96'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1368, 740.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_quadrature_demod_cf_0
|
||||
id: analog_quadrature_demod_cf
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain: '1.0'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [512, 420.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_quadrature_demod_cf_0_0
|
||||
id: analog_quadrature_demod_cf
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain: '1.2'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [520, 572.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: antenna
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [792, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bw
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bandwidth should configure RF filters on some devices.
|
||||
|
||||
Set to 0.0 for automatic calculation.'
|
||||
hide: none
|
||||
label: Bandwidth
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [952, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dc_blocker_xx_0
|
||||
id: dc_blocker_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
length: '1024'
|
||||
long_form: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
type: ff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [896, 564.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decoded_data_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/.satnogs/data/data
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 852.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dev_args
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device arguments
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [336, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: digital_binary_slicer_fb_0_0
|
||||
id: digital_binary_slicer_fb
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1440, 576.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: digital_clock_recovery_mm_xx_0_0_0
|
||||
id: digital_clock_recovery_mm_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain_mu: '0.175'
|
||||
gain_omega: 0.25*0.175*0.175
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mu: '0.5'
|
||||
omega: (audio_samp_rate/100.0) / 200
|
||||
omega_relative_limit: '0.005'
|
||||
type: float
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1248, 540.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: doppler_correction_per_sec
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [176, 852.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_iq_dump
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [272, 772.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: test.wav
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [160, 772.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: gain
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [872, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: iq_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/iq.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [416, 772.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: lo_offset
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'To avoid the SDR carrier at the DC
|
||||
|
||||
we shift the LO a little further'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [712, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_0
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: 'Using the Carson bandwidth rule for filter width:
|
||||
|
||||
width = 2*(deviation + max_modulation_freq).
|
||||
|
||||
For the majority of FM transmissions we can expect
|
||||
|
||||
max_modulation_freq = 3000'
|
||||
cutoff_freq: deviation+max_modulation_freq
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: audio_samp_rate
|
||||
type: fir_filter_ccf
|
||||
width: '3000'
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [320, 524.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_1
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
cutoff_freq: '195'
|
||||
decim: '100'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: audio_samp_rate
|
||||
type: fir_filter_fff
|
||||
width: '10'
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [728, 524.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rigctl_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '4532'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [416, 852.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: root_raised_cosine_filter_0
|
||||
id: root_raised_cosine_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
alpha: '0.5'
|
||||
comment: ''
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
ntaps: '512'
|
||||
samp_rate: '1'
|
||||
sym_rate: '2.4'
|
||||
type: fir_filter_fff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1040, 532.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rx_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e6
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [632, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: samp_rate_rx
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device Sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [480, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_doppler_compensation_0
|
||||
id: satnogs_doppler_compensation
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
compensate: '1'
|
||||
lo_offset: lo_offset
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
out_samp_rate: audio_samp_rate
|
||||
samp_rate: samp_rate_rx
|
||||
sat_freq: rx_freq
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [472, 156.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: satnogs_frame_decoder_0
|
||||
id: satnogs_frame_decoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
decoder_object: variable_amsat_duv_decoder_0
|
||||
itype: byte
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1368, 672.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_frame_file_sink_0_1_0
|
||||
id: satnogs_frame_file_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
output_type: '0'
|
||||
prefix_name: decoded_data_file_path
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1000, 676.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_iq_sink_0
|
||||
id: satnogs_iq_sink
|
||||
parameters:
|
||||
activate: enable_iq_dump
|
||||
affinity: ''
|
||||
alias: ''
|
||||
append: 'False'
|
||||
comment: ''
|
||||
filename: iq_file_path
|
||||
scale: '16768'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [48, 628.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_json_converter_0
|
||||
id: satnogs_json_converter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
extra: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1216, 684.0]
|
||||
rotation: 180
|
||||
state: true
|
||||
- name: satnogs_ogg_encoder_0
|
||||
id: satnogs_ogg_encoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
filename: file_path
|
||||
quality: '1.0'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [704, 404.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_tcp_rigctl_msg_source_0
|
||||
id: satnogs_tcp_rigctl_msg_source
|
||||
parameters:
|
||||
addr: '"127.0.0.1"'
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
interval: int(1000.0/doppler_correction_per_sec) + 1
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mode: 'False'
|
||||
mtu: '1500'
|
||||
port: rigctl_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [216, 268.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_udp_msg_sink_0_0
|
||||
id: satnogs_udp_msg_sink
|
||||
parameters:
|
||||
addr: udp_IP
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
mtu: '1500'
|
||||
port: udp_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1024, 740.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_waterfall_sink_0
|
||||
id: satnogs_waterfall_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
center_freq: rx_freq
|
||||
comment: ''
|
||||
fft_size: '1024'
|
||||
filename: waterfall_file_path
|
||||
mode: '1'
|
||||
rps: '10'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [48, 436.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: soapy_rx_device
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: driver=invalid
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [216, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_source_0
|
||||
id: soapy_source
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amp_gain0: '0'
|
||||
ant0: antenna
|
||||
ant1: RX2
|
||||
args: dev_args
|
||||
balance0: '0'
|
||||
balance1: '0'
|
||||
bw0: bw
|
||||
bw1: '0'
|
||||
center_freq0: rx_freq - lo_offset
|
||||
center_freq1: '0'
|
||||
clock_rate: '0'
|
||||
clock_source: ''
|
||||
comment: ''
|
||||
correction0: '0'
|
||||
correction1: '0'
|
||||
dc_offset0: '0'
|
||||
dc_offset1: '0'
|
||||
dc_offset_auto_mode0: 'False'
|
||||
dc_offset_auto_mode1: 'False'
|
||||
dev: soapy_rx_device
|
||||
devname: custom
|
||||
gain_auto_mode0: 'False'
|
||||
gain_auto_mode1: 'False'
|
||||
ifgr_gain: '59'
|
||||
lna_gain0: '10'
|
||||
lna_gain1: '10'
|
||||
manual_gain0: 'False'
|
||||
manual_gain1: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mix_gain0: '10'
|
||||
mix_gain1: '10'
|
||||
nchan: '1'
|
||||
nco_freq0: '0'
|
||||
nco_freq1: '0'
|
||||
overall_gain0: gain
|
||||
overall_gain1: '10'
|
||||
pga_gain0: '24'
|
||||
pga_gain1: '24'
|
||||
rfgr_gain: '9'
|
||||
samp_rate: samp_rate_rx
|
||||
sdrplay_agc_setpoint: '-30'
|
||||
sdrplay_biastee: 'True'
|
||||
sdrplay_dabnotch: 'False'
|
||||
sdrplay_if_mode: Zero-IF
|
||||
sdrplay_rfnotch: 'False'
|
||||
tia_gain0: '0'
|
||||
tia_gain1: '0'
|
||||
tuner_gain0: '10'
|
||||
tuner_gain1: '10'
|
||||
type: fc32
|
||||
vga_gain0: '10'
|
||||
vga_gain1: '10'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [216, 132.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: udp_IP
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: 127.0.0.1
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [512, 772.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: udp_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '16887'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [512, 852.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: virtual_sink_0
|
||||
id: virtual_sink
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [776, 188.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: virtual_source_0
|
||||
id: virtual_source
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [48, 572.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: waterfall_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/waterfall.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 772.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
connections:
|
||||
- [analog_quadrature_demod_cf_0, '0', satnogs_ogg_encoder_0, '0']
|
||||
- [analog_quadrature_demod_cf_0_0, '0', low_pass_filter_1, '0']
|
||||
- [dc_blocker_xx_0, '0', root_raised_cosine_filter_0, '0']
|
||||
- [digital_binary_slicer_fb_0_0, '0', satnogs_frame_decoder_0, '0']
|
||||
- [digital_clock_recovery_mm_xx_0_0_0, '0', digital_binary_slicer_fb_0_0, '0']
|
||||
- [low_pass_filter_0, '0', analog_quadrature_demod_cf_0, '0']
|
||||
- [low_pass_filter_0, '0', analog_quadrature_demod_cf_0_0, '0']
|
||||
- [low_pass_filter_1, '0', dc_blocker_xx_0, '0']
|
||||
- [root_raised_cosine_filter_0, '0', digital_clock_recovery_mm_xx_0_0_0, '0']
|
||||
- [satnogs_doppler_compensation_0, '0', virtual_sink_0, '0']
|
||||
- [satnogs_frame_decoder_0, out, satnogs_json_converter_0, in]
|
||||
- [satnogs_json_converter_0, out, satnogs_frame_file_sink_0_1_0, frame]
|
||||
- [satnogs_json_converter_0, out, satnogs_udp_msg_sink_0_0, in]
|
||||
- [satnogs_tcp_rigctl_msg_source_0, freq, satnogs_doppler_compensation_0, doppler]
|
||||
- [soapy_source_0, '0', satnogs_doppler_compensation_0, '0']
|
||||
- [virtual_source_0, '0', low_pass_filter_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_iq_sink_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_waterfall_sink_0, '0']
|
||||
|
||||
metadata:
|
||||
file_format: 1
|
|
@ -1,735 +0,0 @@
|
|||
options:
|
||||
parameters:
|
||||
author: Manolis Surligas, George Vardakis
|
||||
category: '[GRC Hier Blocks]'
|
||||
cmake_opt: ''
|
||||
comment: ''
|
||||
copyright: ''
|
||||
description: A NOAA APT Decoder with automatic image synchronization
|
||||
gen_cmake: 'On'
|
||||
gen_linking: dynamic
|
||||
generate_options: no_gui
|
||||
hier_block_src_path: '.:'
|
||||
id: satnogs_noaa_apt_decoder
|
||||
max_nouts: '0'
|
||||
output_language: python
|
||||
placement: (0,0)
|
||||
qt_qss_theme: ''
|
||||
realtime_scheduling: ''
|
||||
run: 'True'
|
||||
run_command: '{python} -u {filename}'
|
||||
run_options: run
|
||||
sizing_mode: fixed
|
||||
thread_safe_setters: ''
|
||||
title: NOAA APT Decoder
|
||||
window_size: 2048,1080
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 8]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
blocks:
|
||||
- name: audio_samp_rate
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '48000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1056, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_wfm_rcv_0
|
||||
id: analog_wfm_rcv
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
audio_decimation: '1'
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
quad_rate: 4*4160*4
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [464, 524.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: antenna
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [792, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: band_pass_filter_0
|
||||
id: band_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
decim: '4'
|
||||
gain: '1'
|
||||
high_cutoff_freq: 4.2e3
|
||||
interp: '1'
|
||||
low_cutoff_freq: '500'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: (4*4160*4 )
|
||||
type: fir_filter_fff
|
||||
width: '200'
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [728, 476.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_complex_to_mag_0
|
||||
id: blocks_complex_to_mag
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1040, 536.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bw
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bandwidth should configure RF filters on some devices.
|
||||
|
||||
Set to 0.0 for automatic calculation.'
|
||||
hide: none
|
||||
label: Bandwidth
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [952, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decoded_data_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/.satnogs/data/data
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 764.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dev_args
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device arguments
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [336, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: doppler_correction_per_sec
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [176, 764.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_iq_dump
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [272, 684.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: test.wav
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [160, 684.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: flip_images
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1176, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: gain
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [880, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: hilbert_fc_0
|
||||
id: hilbert_fc
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
num_taps: '65'
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [904, 532.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: iq_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/iq.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [400, 684.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: lo_offset
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'To avoid the SDR carrier at the DC
|
||||
|
||||
we shift the LO a little further'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [704, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_0_0
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: "Perform a relaxed filter to increase \nthe performance of the auto frequency\n\
|
||||
correction"
|
||||
cutoff_freq: 4*4160*1.1
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: 4*4160*4
|
||||
type: fir_filter_ccf
|
||||
width: 1e3
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [264, 484.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: pfb_arb_resampler_xxx_0
|
||||
id: pfb_arb_resampler_xxx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
atten: '100'
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
nfilts: '32'
|
||||
rrate: audio_samp_rate / (4*4160*4)
|
||||
samp_delay: '0'
|
||||
taps: ''
|
||||
type: fff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [728, 380.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: rational_resampler_xxx_0_0
|
||||
id: rational_resampler_xxx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
decim: '4'
|
||||
fbw: '0'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
taps: ''
|
||||
type: fff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1184, 508.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rigctl_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '4532'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [344, 764.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rx_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e6
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [624, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: samp_rate_rx
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device Sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [472, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_doppler_compensation_0
|
||||
id: satnogs_doppler_compensation
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
compensate: '1'
|
||||
lo_offset: lo_offset
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
out_samp_rate: 4*4160*4
|
||||
samp_rate: samp_rate_rx
|
||||
sat_freq: rx_freq
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [464, 132.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: satnogs_iq_sink_0_0
|
||||
id: satnogs_iq_sink
|
||||
parameters:
|
||||
activate: enable_iq_dump
|
||||
affinity: ''
|
||||
alias: ''
|
||||
append: 'False'
|
||||
comment: ''
|
||||
filename: iq_file_path
|
||||
scale: '16768'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 588.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_noaa_apt_sink_1
|
||||
id: satnogs_noaa_apt_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
filename_png: decoded_data_file_path
|
||||
flip: 'False'
|
||||
height: '1800'
|
||||
sync: 'True'
|
||||
width: '2080'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1144, 612.0]
|
||||
rotation: 180
|
||||
state: true
|
||||
- name: satnogs_ogg_encoder_0
|
||||
id: satnogs_ogg_encoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
filename: file_path
|
||||
quality: '0.8'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [952, 388.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_tcp_rigctl_msg_source_0
|
||||
id: satnogs_tcp_rigctl_msg_source
|
||||
parameters:
|
||||
addr: '"127.0.0.1"'
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
interval: int(1000.0/doppler_correction_per_sec) + 1
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mode: 'False'
|
||||
mtu: '1500'
|
||||
port: rigctl_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [208, 244.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_waterfall_sink_0_0
|
||||
id: satnogs_waterfall_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
center_freq: rx_freq
|
||||
comment: ''
|
||||
fft_size: '1024'
|
||||
filename: waterfall_file_path
|
||||
mode: '1'
|
||||
rps: '10'
|
||||
samp_rate: 4*4160*4
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 404.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: soapy_rx_device
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: driver=invalid
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [216, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_source_0
|
||||
id: soapy_source
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amp_gain0: '0'
|
||||
ant0: antenna
|
||||
ant1: RX2
|
||||
args: dev_args
|
||||
balance0: '0'
|
||||
balance1: '0'
|
||||
bw0: bw
|
||||
bw1: '0'
|
||||
center_freq0: rx_freq - lo_offset
|
||||
center_freq1: '0'
|
||||
clock_rate: '0'
|
||||
clock_source: ''
|
||||
comment: ''
|
||||
correction0: '0'
|
||||
correction1: '0'
|
||||
dc_offset0: '0'
|
||||
dc_offset1: '0'
|
||||
dc_offset_auto_mode0: 'False'
|
||||
dc_offset_auto_mode1: 'False'
|
||||
dev: soapy_rx_device
|
||||
devname: custom
|
||||
gain_auto_mode0: 'False'
|
||||
gain_auto_mode1: 'False'
|
||||
ifgr_gain: '59'
|
||||
lna_gain0: '10'
|
||||
lna_gain1: '10'
|
||||
manual_gain0: 'False'
|
||||
manual_gain1: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mix_gain0: '10'
|
||||
mix_gain1: '10'
|
||||
nchan: '1'
|
||||
nco_freq0: '0'
|
||||
nco_freq1: '0'
|
||||
overall_gain0: gain
|
||||
overall_gain1: '10'
|
||||
pga_gain0: '24'
|
||||
pga_gain1: '24'
|
||||
rfgr_gain: '9'
|
||||
samp_rate: samp_rate_rx
|
||||
sdrplay_agc_setpoint: '-30'
|
||||
sdrplay_biastee: 'True'
|
||||
sdrplay_dabnotch: 'False'
|
||||
sdrplay_if_mode: Zero-IF
|
||||
sdrplay_rfnotch: 'False'
|
||||
tia_gain0: '0'
|
||||
tia_gain1: '0'
|
||||
tuner_gain0: '10'
|
||||
tuner_gain1: '10'
|
||||
type: fc32
|
||||
vga_gain0: '10'
|
||||
vga_gain1: '10'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [208, 108.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: sync
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1264, 12.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: udp_IP
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: 127.0.0.1
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [512, 684.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: udp_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '16887'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [440, 764.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: virtual_sink_0
|
||||
id: virtual_sink
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [768, 164.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: virtual_source_0
|
||||
id: virtual_source
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 532.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: waterfall_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/waterfall.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [16, 684.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
connections:
|
||||
- [analog_wfm_rcv_0, '0', band_pass_filter_0, '0']
|
||||
- [analog_wfm_rcv_0, '0', pfb_arb_resampler_xxx_0, '0']
|
||||
- [band_pass_filter_0, '0', hilbert_fc_0, '0']
|
||||
- [blocks_complex_to_mag_0, '0', rational_resampler_xxx_0_0, '0']
|
||||
- [hilbert_fc_0, '0', blocks_complex_to_mag_0, '0']
|
||||
- [low_pass_filter_0_0, '0', analog_wfm_rcv_0, '0']
|
||||
- [pfb_arb_resampler_xxx_0, '0', satnogs_ogg_encoder_0, '0']
|
||||
- [rational_resampler_xxx_0_0, '0', satnogs_noaa_apt_sink_1, '0']
|
||||
- [satnogs_doppler_compensation_0, '0', virtual_sink_0, '0']
|
||||
- [satnogs_tcp_rigctl_msg_source_0, freq, satnogs_doppler_compensation_0, doppler]
|
||||
- [soapy_source_0, '0', satnogs_doppler_compensation_0, '0']
|
||||
- [virtual_source_0, '0', low_pass_filter_0_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_iq_sink_0_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_waterfall_sink_0_0, '0']
|
||||
|
||||
metadata:
|
||||
file_format: 1
|
|
@ -1,982 +0,0 @@
|
|||
options:
|
||||
parameters:
|
||||
author: Manolis Surligas (surligas@gmail.com)
|
||||
category: '[GRC Hier Blocks]'
|
||||
cmake_opt: ''
|
||||
comment: ''
|
||||
copyright: ''
|
||||
description: FSK 9600 Decoder for the Reaktor-Hello-World satellite
|
||||
gen_cmake: 'On'
|
||||
gen_linking: dynamic
|
||||
generate_options: no_gui
|
||||
hier_block_src_path: '.:'
|
||||
id: satnogs_reaktor_hello_world_fsk9600_decoder
|
||||
max_nouts: '0'
|
||||
output_language: python
|
||||
placement: (0,0)
|
||||
qt_qss_theme: ''
|
||||
realtime_scheduling: ''
|
||||
run: 'True'
|
||||
run_command: '{python} -u {filename}'
|
||||
run_options: run
|
||||
sizing_mode: fixed
|
||||
thread_safe_setters: ''
|
||||
title: satnogs_reaktor_hello_world_fsk9600_decoder
|
||||
window_size: 2*1080,1080
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 20]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
blocks:
|
||||
- name: audio_samp_rate
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: '48000'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1264, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decimation
|
||||
id: variable
|
||||
parameters:
|
||||
comment: ''
|
||||
value: satnogs.find_decimation(baudrate, 2, audio_samp_rate)
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1056, 28.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: variable_ieee802_15_4_variant_decoder_0
|
||||
id: variable_ieee802_15_4_variant_decoder
|
||||
parameters:
|
||||
comment: ''
|
||||
crc: satnogs.crc.CRC16_IBM
|
||||
frame_len: '256'
|
||||
preamble: '[0x55, 0x55, 0x55, 0x55, 0x55]'
|
||||
preamble_thrsh: '2'
|
||||
sync_thrsh: '1'
|
||||
sync_word: '[0x35, 0x2E, 0x35, 0x2E]'
|
||||
var_len: 'True'
|
||||
whitening: variable_whitening_0
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1064, 900.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: variable_whitening_0
|
||||
id: variable_whitening
|
||||
parameters:
|
||||
comment: ''
|
||||
mask: '0x21'
|
||||
order: '8'
|
||||
seed: '0x1FF'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [920, 932.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_quadrature_demod_cf_0_0
|
||||
id: analog_quadrature_demod_cf
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain: '1.2'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1240, 468.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_quadrature_demod_cf_0_0_0
|
||||
id: analog_quadrature_demod_cf
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain: '0.9'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [496, 348.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: analog_quadrature_demod_cf_0_0_0_0
|
||||
id: analog_quadrature_demod_cf
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain: '1.0'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [432, 532.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: antenna
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [800, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: baudrate
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '9600.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1168, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_delay_0
|
||||
id: blocks_delay
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
delay: 1024//2
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
num_ports: '1'
|
||||
type: complex
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [448, 452.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_moving_average_xx_0
|
||||
id: blocks_moving_average_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
length: '1024'
|
||||
max_iter: '4096'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
scale: 1.0/1024.0
|
||||
type: float
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [584, 508.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_multiply_xx_0
|
||||
id: blocks_multiply_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
num_inputs: '2'
|
||||
type: complex
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [952, 456.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: blocks_vco_c_0
|
||||
id: blocks_vco_c
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amplitude: '1.0'
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: baudrate*decimation
|
||||
sensitivity: -baudrate*decimation
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [760, 516.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: bw
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'The bandwidth should configure RF filters on some devices.
|
||||
|
||||
Set to 0.0 for automatic calculation.'
|
||||
hide: none
|
||||
label: Bandwidth
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [952, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dc_blocker_xx_0
|
||||
id: dc_blocker_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
length: '1024'
|
||||
long_form: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
type: ff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1424, 668.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: dc_blocker_xx_0_0
|
||||
id: dc_blocker_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
length: '1024'
|
||||
long_form: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
type: ff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [904, 340.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: decoded_data_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/.satnogs/data/data
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 876.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: dev_args
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device arguments
|
||||
short_id: ''
|
||||
type: str
|
||||
value: ''
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [352, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: digital_binary_slicer_fb_0
|
||||
id: digital_binary_slicer_fb
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1104, 680.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: digital_clock_recovery_mm_xx_0
|
||||
id: digital_clock_recovery_mm_xx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
gain_mu: 0.5/8.0
|
||||
gain_omega: 2 * math.pi / 100
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mu: '0.5'
|
||||
omega: '2'
|
||||
omega_relative_limit: '0.01'
|
||||
type: float
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1224, 644.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: doppler_correction_per_sec
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '20'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [168, 876.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: enable_iq_dump
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [264, 796.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: test.wav
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [152, 796.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: gain
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [880, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: import_0
|
||||
id: import
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
imports: import math
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [0, 172.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: iq_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/iq.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [408, 796.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: lo_offset
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: 'To avoid the SDR carrier at the DC
|
||||
|
||||
we shift the LO a little further'
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e3
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [720, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_0
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
cutoff_freq: 0.75 * baudrate
|
||||
decim: decimation // 2
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: baudrate*decimation
|
||||
type: fir_filter_ccf
|
||||
width: baudrate / 8.0
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1072, 420.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_0_0
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: "Perform a relaxed filter to increase \nthe performance of the auto frequency\n\
|
||||
correction"
|
||||
cutoff_freq: baudrate*1.25
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: baudrate*decimation
|
||||
type: fir_filter_ccf
|
||||
width: baudrate / 2.0
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [264, 484.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: low_pass_filter_1
|
||||
id: low_pass_filter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
beta: '6.76'
|
||||
comment: ''
|
||||
cutoff_freq: baudrate * 0.60
|
||||
decim: '1'
|
||||
gain: '1'
|
||||
interp: '1'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
samp_rate: 2 * baudrate
|
||||
type: fir_filter_fff
|
||||
width: baudrate / 8.0
|
||||
win: firdes.WIN_HAMMING
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1400, 420.0]
|
||||
rotation: 0
|
||||
state: bypassed
|
||||
- name: pfb_arb_resampler_xxx_1
|
||||
id: pfb_arb_resampler_xxx
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
atten: '80'
|
||||
comment: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
nfilts: '32'
|
||||
rrate: audio_samp_rate / (baudrate*decimation)
|
||||
samp_delay: '0'
|
||||
taps: ''
|
||||
type: fff
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [672, 324.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: rigctl_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '4532'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [408, 892.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: rx_freq
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: 100e6
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [640, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: samp_rate_rx
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: Device Sampling rate
|
||||
short_id: ''
|
||||
type: eng_float
|
||||
value: '0.0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [488, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_doppler_compensation_0
|
||||
id: satnogs_doppler_compensation
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
compensate: '1'
|
||||
lo_offset: lo_offset
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
out_samp_rate: baudrate*decimation
|
||||
samp_rate: samp_rate_rx
|
||||
sat_freq: rx_freq
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [480, 140.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: satnogs_frame_decoder_0_0
|
||||
id: satnogs_frame_decoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
decoder_object: variable_ieee802_15_4_variant_decoder_0
|
||||
itype: byte
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
vlen: '1'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [888, 680.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_frame_file_sink_0_1_0
|
||||
id: satnogs_frame_file_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
output_type: '0'
|
||||
prefix_name: decoded_data_file_path
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [496, 660.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_iq_sink_0
|
||||
id: satnogs_iq_sink
|
||||
parameters:
|
||||
activate: enable_iq_dump
|
||||
affinity: ''
|
||||
alias: ''
|
||||
append: 'False'
|
||||
comment: ''
|
||||
filename: iq_file_path
|
||||
scale: '16768'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [24, 508.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_json_converter_0
|
||||
id: satnogs_json_converter
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
extra: ''
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [720, 692.0]
|
||||
rotation: 180
|
||||
state: true
|
||||
- name: satnogs_ogg_encoder_0
|
||||
id: satnogs_ogg_encoder
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
filename: file_path
|
||||
quality: '1.0'
|
||||
samp_rate: audio_samp_rate
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [1056, 332.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_tcp_rigctl_msg_source_0
|
||||
id: satnogs_tcp_rigctl_msg_source
|
||||
parameters:
|
||||
addr: '"127.0.0.1"'
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
interval: int(1000.0/doppler_correction_per_sec) + 1
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mode: 'False'
|
||||
mtu: '1500'
|
||||
port: rigctl_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [224, 252.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: satnogs_udp_msg_sink_0_0
|
||||
id: satnogs_udp_msg_sink
|
||||
parameters:
|
||||
addr: udp_IP
|
||||
affinity: ''
|
||||
alias: ''
|
||||
comment: ''
|
||||
mtu: '1500'
|
||||
port: udp_port
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [520, 724.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: satnogs_waterfall_sink_0
|
||||
id: satnogs_waterfall_sink
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
center_freq: rx_freq
|
||||
comment: ''
|
||||
fft_size: '1024'
|
||||
filename: waterfall_file_path
|
||||
mode: '1'
|
||||
rps: '10'
|
||||
samp_rate: baudrate*decimation
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [24, 316.0]
|
||||
rotation: 180
|
||||
state: enabled
|
||||
- name: soapy_rx_device
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: driver=invalid
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [224, 28.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: soapy_source_0
|
||||
id: soapy_source
|
||||
parameters:
|
||||
affinity: ''
|
||||
alias: ''
|
||||
amp_gain0: '0'
|
||||
ant0: antenna
|
||||
ant1: RX2
|
||||
args: dev_args
|
||||
balance0: '0'
|
||||
balance1: '0'
|
||||
bw0: bw
|
||||
bw1: '0'
|
||||
center_freq0: rx_freq - lo_offset
|
||||
center_freq1: '0'
|
||||
clock_rate: '0'
|
||||
clock_source: ''
|
||||
comment: ''
|
||||
correction0: '0'
|
||||
correction1: '0'
|
||||
dc_offset0: '0'
|
||||
dc_offset1: '0'
|
||||
dc_offset_auto_mode0: 'False'
|
||||
dc_offset_auto_mode1: 'False'
|
||||
dev: soapy_rx_device
|
||||
devname: custom
|
||||
gain_auto_mode0: 'False'
|
||||
gain_auto_mode1: 'False'
|
||||
ifgr_gain: '59'
|
||||
lna_gain0: '10'
|
||||
lna_gain1: '10'
|
||||
manual_gain0: 'False'
|
||||
manual_gain1: 'True'
|
||||
maxoutbuf: '0'
|
||||
minoutbuf: '0'
|
||||
mix_gain0: '10'
|
||||
mix_gain1: '10'
|
||||
nchan: '1'
|
||||
nco_freq0: '0'
|
||||
nco_freq1: '0'
|
||||
overall_gain0: gain
|
||||
overall_gain1: '10'
|
||||
pga_gain0: '24'
|
||||
pga_gain1: '24'
|
||||
rfgr_gain: '9'
|
||||
samp_rate: samp_rate_rx
|
||||
sdrplay_agc_setpoint: '-30'
|
||||
sdrplay_biastee: 'True'
|
||||
sdrplay_dabnotch: 'False'
|
||||
sdrplay_if_mode: Zero-IF
|
||||
sdrplay_rfnotch: 'False'
|
||||
tia_gain0: '0'
|
||||
tia_gain1: '0'
|
||||
tuner_gain0: '10'
|
||||
tuner_gain1: '10'
|
||||
type: fc32
|
||||
vga_gain0: '10'
|
||||
vga_gain1: '10'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [224, 116.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: udp_IP
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: 127.0.0.1
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [504, 796.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: udp_port
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: intx
|
||||
value: '16887'
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [504, 892.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
- name: virtual_sink_0
|
||||
id: virtual_sink
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [784, 172.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: virtual_source_0
|
||||
id: virtual_source
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
stream_id: doppler_corrected
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [24, 452.0]
|
||||
rotation: 0
|
||||
state: true
|
||||
- name: waterfall_file_path
|
||||
id: parameter
|
||||
parameters:
|
||||
alias: ''
|
||||
comment: ''
|
||||
hide: none
|
||||
label: ''
|
||||
short_id: ''
|
||||
type: str
|
||||
value: /tmp/waterfall.dat
|
||||
states:
|
||||
bus_sink: false
|
||||
bus_source: false
|
||||
bus_structure: null
|
||||
coordinate: [8, 796.0]
|
||||
rotation: 0
|
||||
state: enabled
|
||||
|
||||
connections:
|
||||
- [analog_quadrature_demod_cf_0_0, '0', low_pass_filter_1, '0']
|
||||
- [analog_quadrature_demod_cf_0_0_0, '0', pfb_arb_resampler_xxx_1, '0']
|
||||
- [analog_quadrature_demod_cf_0_0_0_0, '0', blocks_moving_average_xx_0, '0']
|
||||
- [blocks_delay_0, '0', blocks_multiply_xx_0, '0']
|
||||
- [blocks_moving_average_xx_0, '0', blocks_vco_c_0, '0']
|
||||
- [blocks_multiply_xx_0, '0', low_pass_filter_0, '0']
|
||||
- [blocks_vco_c_0, '0', blocks_multiply_xx_0, '1']
|
||||
- [dc_blocker_xx_0, '0', digital_clock_recovery_mm_xx_0, '0']
|
||||
- [dc_blocker_xx_0_0, '0', satnogs_ogg_encoder_0, '0']
|
||||
- [digital_binary_slicer_fb_0, '0', satnogs_frame_decoder_0_0, '0']
|
||||
- [digital_clock_recovery_mm_xx_0, '0', digital_binary_slicer_fb_0, '0']
|
||||
- [low_pass_filter_0, '0', analog_quadrature_demod_cf_0_0, '0']
|
||||
- [low_pass_filter_0_0, '0', analog_quadrature_demod_cf_0_0_0_0, '0']
|
||||
- [low_pass_filter_1, '0', dc_blocker_xx_0, '0']
|
||||
- [pfb_arb_resampler_xxx_1, '0', dc_blocker_xx_0_0, '0']
|
||||
- [satnogs_doppler_compensation_0, '0', virtual_sink_0, '0']
|
||||
- [satnogs_frame_decoder_0_0, out, satnogs_json_converter_0, in]
|
||||
- [satnogs_json_converter_0, out, satnogs_frame_file_sink_0_1_0, frame]
|
||||
- [satnogs_json_converter_0, out, satnogs_udp_msg_sink_0_0, in]
|
||||
- [satnogs_tcp_rigctl_msg_source_0, freq, satnogs_doppler_compensation_0, doppler]
|
||||
- [soapy_source_0, '0', satnogs_doppler_compensation_0, '0']
|
||||
- [virtual_source_0, '0', analog_quadrature_demod_cf_0_0_0, '0']
|
||||
- [virtual_source_0, '0', blocks_delay_0, '0']
|
||||
- [virtual_source_0, '0', low_pass_filter_0_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_iq_sink_0, '0']
|
||||
- [virtual_source_0, '0', satnogs_waterfall_sink_0, '0']
|
||||
|
||||
metadata:
|
||||
file_format: 1
|
|
@ -1,443 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: AMSAT FOX DUV Decoder
|
||||
# Author: Thanos Giolias (agiolias@csd.uoc.gr), Nikos Karamolegos (karamolegkos.n@gmail.com), Manolis Surligas (surligas@gmail.com)
|
||||
# Description: A DUV Decoder for the AMSAT FOX satellites
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
import math
|
||||
from gnuradio import digital
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_amsat_fox_duv_decoder(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "AMSAT FOX DUV Decoder")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.variable_amsat_duv_decoder_0 = variable_amsat_duv_decoder_0 = satnogs.amsat_duv_decoder_make('0011111010', 96)
|
||||
self.max_modulation_freq = max_modulation_freq = 3000
|
||||
self.deviation = deviation = 5000
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(audio_samp_rate, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_json_converter_0 = satnogs.json_converter()
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_frame_decoder_0 = satnogs.frame_decoder(variable_amsat_duv_decoder_0, 1 * 1)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, audio_samp_rate, 1)
|
||||
self.root_raised_cosine_filter_0 = filter.fir_filter_fff(
|
||||
1,
|
||||
firdes.root_raised_cosine(
|
||||
1,
|
||||
1,
|
||||
2.4,
|
||||
0.5,
|
||||
512))
|
||||
self.low_pass_filter_1 = filter.fir_filter_fff(
|
||||
100,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
195,
|
||||
10,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
deviation+max_modulation_freq,
|
||||
3000,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.digital_clock_recovery_mm_xx_0_0_0 = digital.clock_recovery_mm_ff((audio_samp_rate/100.0) / 200, 0.25*0.175*0.175, 0.5, 0.175, 0.005)
|
||||
self.digital_binary_slicer_fb_0_0 = digital.binary_slicer_fb()
|
||||
self.dc_blocker_xx_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf(1.2)
|
||||
self.analog_quadrature_demod_cf_0 = analog.quadrature_demod_cf(1.0)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_frame_decoder_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_frame_file_sink_0_1_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_quadrature_demod_cf_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.low_pass_filter_1, 0))
|
||||
self.connect((self.dc_blocker_xx_0, 0), (self.root_raised_cosine_filter_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0_0, 0), (self.satnogs_frame_decoder_0, 0))
|
||||
self.connect((self.digital_clock_recovery_mm_xx_0_0_0, 0), (self.digital_binary_slicer_fb_0_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.analog_quadrature_demod_cf_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.analog_quadrature_demod_cf_0_0, 0))
|
||||
self.connect((self.low_pass_filter_1, 0), (self.dc_blocker_xx_0, 0))
|
||||
self.connect((self.root_raised_cosine_filter_0, 0), (self.digital_clock_recovery_mm_xx_0_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.low_pass_filter_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_variable_amsat_duv_decoder_0(self):
|
||||
return self.variable_amsat_duv_decoder_0
|
||||
|
||||
def set_variable_amsat_duv_decoder_0(self, variable_amsat_duv_decoder_0):
|
||||
self.variable_amsat_duv_decoder_0 = variable_amsat_duv_decoder_0
|
||||
|
||||
def get_max_modulation_freq(self):
|
||||
return self.max_modulation_freq
|
||||
|
||||
def set_max_modulation_freq(self, max_modulation_freq):
|
||||
self.max_modulation_freq = max_modulation_freq
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_deviation(self):
|
||||
return self.deviation
|
||||
|
||||
def set_deviation(self, deviation):
|
||||
self.deviation = deviation
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.digital_clock_recovery_mm_xx_0_0_0.set_omega((self.audio_samp_rate/100.0) / 200)
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 3000, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate, 195, 10, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'A DUV Decoder for the AMSAT FOX satellites'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_amsat_fox_duv_decoder, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,367 +0,0 @@
|
|||
#!/usr/bin/env python2
|
||||
# -*- coding: utf-8 -*-
|
||||
##################################################
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: satnogs_meteor_decoder
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: METEOR CCSDS Decoder
|
||||
# GNU Radio version: 3.7.13.5
|
||||
##################################################
|
||||
|
||||
|
||||
from gnuradio import analog
|
||||
from gnuradio import blocks
|
||||
from gnuradio import digital
|
||||
from gnuradio import eng_notation
|
||||
from gnuradio import gr
|
||||
from gnuradio.eng_option import eng_option
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio.filter import pfb
|
||||
from optparse import OptionParser
|
||||
import math
|
||||
import osmosdr
|
||||
import satnogs
|
||||
import time
|
||||
|
||||
|
||||
class satnogs_meteor_decoder(gr.top_block):
|
||||
|
||||
def __init__(self, antenna=satnogs.not_set_antenna, baudrate=9600.0, bb_gain=satnogs.not_set_rx_bb_gain, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args=satnogs.not_set_dev_args, doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', if_gain=satnogs.not_set_rx_if_gain, iq_file_path='/tmp/iq.dat', lo_offset=100e3, ppm=0, rf_gain=satnogs.not_set_rx_rf_gain, rigctl_port=4532, rx_freq=100e6, rx_sdr_device='usrpb200', samp_rate_rx=satnogs.not_set_samp_rate_rx, udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "satnogs_meteor_decoder")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.baudrate = baudrate
|
||||
self.bb_gain = bb_gain
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.if_gain = if_gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.ppm = ppm
|
||||
self.rf_gain = rf_gain
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.rx_sdr_device = rx_sdr_device
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.sps = sps = 2
|
||||
self.nfilts = nfilts = 32
|
||||
self.ntaps = ntaps = 11 * sps * nfilts
|
||||
|
||||
self.rrc_taps = rrc_taps = firdes.root_raised_cosine(nfilts, nfilts * sps, 1.0, 0.35, ntaps)
|
||||
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink((sps*72e3) , 0.0, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_lrpt_sync_0 = satnogs.lrpt_sync(2)
|
||||
self.satnogs_lrpt_decoder_0 = satnogs.lrpt_decoder()
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_coarse_doppler_correction_cc_0 = satnogs.coarse_doppler_correction_cc(rx_freq, satnogs.handle_samp_rate_rx(rx_sdr_device, samp_rate_rx))
|
||||
self.pfb_arb_resampler_xxx_0 = pfb.arb_resampler_ccf(
|
||||
(sps*72e3) / satnogs.handle_samp_rate_rx(rx_sdr_device, samp_rate_rx),
|
||||
taps=None,
|
||||
flt_size=32)
|
||||
self.pfb_arb_resampler_xxx_0.declare_sample_delay(0)
|
||||
|
||||
self.osmosdr_source_0 = osmosdr.source( args="numchan=" + str(1) + " " + satnogs.handle_rx_dev_args(rx_sdr_device, dev_args) )
|
||||
self.osmosdr_source_0.set_sample_rate(satnogs.handle_samp_rate_rx(rx_sdr_device, samp_rate_rx))
|
||||
self.osmosdr_source_0.set_center_freq(rx_freq - lo_offset, 0)
|
||||
self.osmosdr_source_0.set_freq_corr(ppm, 0)
|
||||
self.osmosdr_source_0.set_dc_offset_mode(2, 0)
|
||||
self.osmosdr_source_0.set_iq_balance_mode(0, 0)
|
||||
self.osmosdr_source_0.set_gain_mode(False, 0)
|
||||
self.osmosdr_source_0.set_gain(satnogs.handle_rx_rf_gain(rx_sdr_device, rf_gain), 0)
|
||||
self.osmosdr_source_0.set_if_gain(satnogs.handle_rx_if_gain(rx_sdr_device, if_gain), 0)
|
||||
self.osmosdr_source_0.set_bb_gain(satnogs.handle_rx_bb_gain(rx_sdr_device, bb_gain), 0)
|
||||
self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(rx_sdr_device, antenna), 0)
|
||||
self.osmosdr_source_0.set_bandwidth(satnogs.handle_samp_rate_rx(rx_sdr_device, samp_rate_rx), 0)
|
||||
|
||||
self.digital_pfb_clock_sync_xxx_0 = digital.pfb_clock_sync_ccf(sps, 2*math.pi/100.0, (rrc_taps), nfilts, nfilts//2, 1.5, 1)
|
||||
self.digital_costas_loop_cc_0 = digital.costas_loop_cc(2*math.pi/100.0, 4, False)
|
||||
self.blocks_rotator_cc_0 = blocks.rotator_cc(-2.0 * math.pi * (lo_offset / satnogs.handle_samp_rate_rx(rx_sdr_device, samp_rate_rx)))
|
||||
self.analog_agc2_xx_0 = analog.agc2_cc(0.6e-1, 1e-3, 1.0, 1.0)
|
||||
self.analog_agc2_xx_0.set_max_gain(65536)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_lrpt_decoder_0, 'frame'), (self.satnogs_frame_file_sink_0_1_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_lrpt_decoder_0, 'frame'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_lrpt_sync_0, 'cadu'), (self.satnogs_lrpt_decoder_0, 'cadu'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_coarse_doppler_correction_cc_0, 'freq'))
|
||||
self.connect((self.analog_agc2_xx_0, 0), (self.digital_pfb_clock_sync_xxx_0, 0))
|
||||
self.connect((self.blocks_rotator_cc_0, 0), (self.satnogs_coarse_doppler_correction_cc_0, 0))
|
||||
self.connect((self.digital_costas_loop_cc_0, 0), (self.satnogs_lrpt_sync_0, 0))
|
||||
self.connect((self.digital_pfb_clock_sync_xxx_0, 0), (self.digital_costas_loop_cc_0, 0))
|
||||
self.connect((self.osmosdr_source_0, 0), (self.blocks_rotator_cc_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_0, 0), (self.analog_agc2_xx_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.satnogs_coarse_doppler_correction_cc_0, 0), (self.pfb_arb_resampler_xxx_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(self.rx_sdr_device, self.antenna), 0)
|
||||
|
||||
def get_baudrate(self):
|
||||
return self.baudrate
|
||||
|
||||
def set_baudrate(self, baudrate):
|
||||
self.baudrate = baudrate
|
||||
|
||||
def get_bb_gain(self):
|
||||
return self.bb_gain
|
||||
|
||||
def set_bb_gain(self, bb_gain):
|
||||
self.bb_gain = bb_gain
|
||||
self.osmosdr_source_0.set_bb_gain(satnogs.handle_rx_bb_gain(self.rx_sdr_device, self.bb_gain), 0)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_if_gain(self):
|
||||
return self.if_gain
|
||||
|
||||
def set_if_gain(self, if_gain):
|
||||
self.if_gain = if_gain
|
||||
self.osmosdr_source_0.set_if_gain(satnogs.handle_rx_if_gain(self.rx_sdr_device, self.if_gain), 0)
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.osmosdr_source_0.set_center_freq(self.rx_freq - self.lo_offset, 0)
|
||||
self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * (self.lo_offset / satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx)))
|
||||
|
||||
def get_ppm(self):
|
||||
return self.ppm
|
||||
|
||||
def set_ppm(self, ppm):
|
||||
self.ppm = ppm
|
||||
self.osmosdr_source_0.set_freq_corr(self.ppm, 0)
|
||||
|
||||
def get_rf_gain(self):
|
||||
return self.rf_gain
|
||||
|
||||
def set_rf_gain(self, rf_gain):
|
||||
self.rf_gain = rf_gain
|
||||
self.osmosdr_source_0.set_gain(satnogs.handle_rx_rf_gain(self.rx_sdr_device, self.rf_gain), 0)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.satnogs_coarse_doppler_correction_cc_0.set_new_freq_locked(self.rx_freq)
|
||||
self.osmosdr_source_0.set_center_freq(self.rx_freq - self.lo_offset, 0)
|
||||
|
||||
def get_rx_sdr_device(self):
|
||||
return self.rx_sdr_device
|
||||
|
||||
def set_rx_sdr_device(self, rx_sdr_device):
|
||||
self.rx_sdr_device = rx_sdr_device
|
||||
self.pfb_arb_resampler_xxx_0.set_rate((self.sps*72e3) / satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx))
|
||||
self.osmosdr_source_0.set_sample_rate(satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx))
|
||||
self.osmosdr_source_0.set_gain(satnogs.handle_rx_rf_gain(self.rx_sdr_device, self.rf_gain), 0)
|
||||
self.osmosdr_source_0.set_if_gain(satnogs.handle_rx_if_gain(self.rx_sdr_device, self.if_gain), 0)
|
||||
self.osmosdr_source_0.set_bb_gain(satnogs.handle_rx_bb_gain(self.rx_sdr_device, self.bb_gain), 0)
|
||||
self.osmosdr_source_0.set_antenna(satnogs.handle_rx_antenna(self.rx_sdr_device, self.antenna), 0)
|
||||
self.osmosdr_source_0.set_bandwidth(satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx), 0)
|
||||
self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * (self.lo_offset / satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx)))
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.pfb_arb_resampler_xxx_0.set_rate((self.sps*72e3) / satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx))
|
||||
self.osmosdr_source_0.set_sample_rate(satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx))
|
||||
self.osmosdr_source_0.set_bandwidth(satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx), 0)
|
||||
self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * (self.lo_offset / satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx)))
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_sps(self):
|
||||
return self.sps
|
||||
|
||||
def set_sps(self, sps):
|
||||
self.sps = sps
|
||||
self.pfb_arb_resampler_xxx_0.set_rate((self.sps*72e3) / satnogs.handle_samp_rate_rx(self.rx_sdr_device, self.samp_rate_rx))
|
||||
self.set_ntaps(11 * self.sps * self.nfilts)
|
||||
|
||||
def get_nfilts(self):
|
||||
return self.nfilts
|
||||
|
||||
def set_nfilts(self, nfilts):
|
||||
self.nfilts = nfilts
|
||||
self.set_ntaps(11 * self.sps * self.nfilts)
|
||||
|
||||
def get_ntaps(self):
|
||||
return self.ntaps
|
||||
|
||||
def set_ntaps(self, ntaps):
|
||||
self.ntaps = ntaps
|
||||
|
||||
def get_rrc_taps(self):
|
||||
return self.rrc_taps
|
||||
|
||||
def set_rrc_taps(self, rrc_taps):
|
||||
self.rrc_taps = rrc_taps
|
||||
self.digital_pfb_clock_sync_xxx_0.update_taps((self.rrc_taps))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'METEOR CCSDS Decoder'
|
||||
parser = OptionParser(usage="%prog: [options]", option_class=eng_option, description=description)
|
||||
parser.add_option(
|
||||
"", "--antenna", dest="antenna", type="string", default=satnogs.not_set_antenna,
|
||||
help="Set antenna [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--baudrate", dest="baudrate", type="eng_float", default=eng_notation.num_to_str(9600.0),
|
||||
help="Set baudrate [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--bb-gain", dest="bb_gain", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_rx_bb_gain),
|
||||
help="Set bb_gain [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--decoded-data-file-path", dest="decoded_data_file_path", type="string", default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--dev-args", dest="dev_args", type="string", default=satnogs.not_set_dev_args,
|
||||
help="Set dev_args [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--doppler-correction-per-sec", dest="doppler_correction_per_sec", type="intx", default=20,
|
||||
help="Set doppler_correction_per_sec [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--enable-iq-dump", dest="enable_iq_dump", type="intx", default=0,
|
||||
help="Set enable_iq_dump [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--file-path", dest="file_path", type="string", default='test.wav',
|
||||
help="Set file_path [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--if-gain", dest="if_gain", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_rx_if_gain),
|
||||
help="Set if_gain [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--iq-file-path", dest="iq_file_path", type="string", default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--lo-offset", dest="lo_offset", type="eng_float", default=eng_notation.num_to_str(100e3),
|
||||
help="Set lo_offset [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--ppm", dest="ppm", type="intx", default=0,
|
||||
help="Set ppm [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--rf-gain", dest="rf_gain", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_rx_rf_gain),
|
||||
help="Set rf_gain [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--rigctl-port", dest="rigctl_port", type="intx", default=4532,
|
||||
help="Set rigctl_port [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--rx-freq", dest="rx_freq", type="eng_float", default=eng_notation.num_to_str(100e6),
|
||||
help="Set rx_freq [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--rx-sdr-device", dest="rx_sdr_device", type="string", default='usrpb200',
|
||||
help="Set rx_sdr_device [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--samp-rate-rx", dest="samp_rate_rx", type="eng_float", default=eng_notation.num_to_str(satnogs.not_set_samp_rate_rx),
|
||||
help="Set samp_rate_rx [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--udp-IP", dest="udp_IP", type="string", default='127.0.0.1',
|
||||
help="Set udp_IP [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--udp-port", dest="udp_port", type="intx", default=16887,
|
||||
help="Set udp_port [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--waterfall-file-path", dest="waterfall_file_path", type="string", default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%default]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_meteor_decoder, options=None):
|
||||
if options is None:
|
||||
options, _ = argument_parser().parse_args()
|
||||
|
||||
tb = top_block_cls(antenna=options.antenna, baudrate=options.baudrate, bb_gain=options.bb_gain, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, if_gain=options.if_gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, ppm=options.ppm, rf_gain=options.rf_gain, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, rx_sdr_device=options.rx_sdr_device, samp_rate_rx=options.samp_rate_rx, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,435 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: NOAA APT Decoder
|
||||
# Author: Manolis Surligas, George Vardakis
|
||||
# Description: A NOAA APT Decoder with automatic image synchronization
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
from gnuradio import blocks
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
from gnuradio.filter import pfb
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_noaa_apt_decoder(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', flip_images=0, gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', sync=1, udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "NOAA APT Decoder")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.flip_images = flip_images
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.sync = sync
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0_0 = satnogs.waterfall_sink(4*4160*4, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 0.8)
|
||||
self.satnogs_noaa_apt_sink_1 = satnogs.noaa_apt_sink(decoded_data_file_path, 2080, 1800, True, False)
|
||||
self.satnogs_iq_sink_0_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, 4*4160*4, 1)
|
||||
self.rational_resampler_xxx_0_0 = filter.rational_resampler_fff(
|
||||
interpolation=1,
|
||||
decimation=4,
|
||||
taps=None,
|
||||
fractional_bw=None)
|
||||
self.pfb_arb_resampler_xxx_0 = pfb.arb_resampler_fff(
|
||||
audio_samp_rate / (4*4160*4),
|
||||
taps=None,
|
||||
flt_size=32)
|
||||
self.pfb_arb_resampler_xxx_0.declare_sample_delay(0)
|
||||
self.low_pass_filter_0_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
4*4160*4,
|
||||
4*4160*1.1,
|
||||
1e3,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.hilbert_fc_0 = filter.hilbert_fc(65, firdes.WIN_HAMMING, 6.76)
|
||||
self.blocks_complex_to_mag_0 = blocks.complex_to_mag(1)
|
||||
self.band_pass_filter_0 = filter.fir_filter_fff(
|
||||
4,
|
||||
firdes.band_pass(
|
||||
1,
|
||||
(4*4160*4 ),
|
||||
500,
|
||||
4.2e3,
|
||||
200,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.analog_wfm_rcv_0 = analog.wfm_rcv(
|
||||
quad_rate=4*4160*4,
|
||||
audio_decimation=1,
|
||||
)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_wfm_rcv_0, 0), (self.band_pass_filter_0, 0))
|
||||
self.connect((self.analog_wfm_rcv_0, 0), (self.pfb_arb_resampler_xxx_0, 0))
|
||||
self.connect((self.band_pass_filter_0, 0), (self.hilbert_fc_0, 0))
|
||||
self.connect((self.blocks_complex_to_mag_0, 0), (self.rational_resampler_xxx_0_0, 0))
|
||||
self.connect((self.hilbert_fc_0, 0), (self.blocks_complex_to_mag_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.analog_wfm_rcv_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.rational_resampler_xxx_0_0, 0), (self.satnogs_noaa_apt_sink_1, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.low_pass_filter_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_flip_images(self):
|
||||
return self.flip_images
|
||||
|
||||
def set_flip_images(self, flip_images):
|
||||
self.flip_images = flip_images
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_sync(self):
|
||||
return self.sync
|
||||
|
||||
def set_sync(self, sync):
|
||||
self.sync = sync
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.audio_samp_rate / (4*4160*4))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'A NOAA APT Decoder with automatic image synchronization'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--flip-images", dest="flip_images", type=intx, default=0,
|
||||
help="Set flip_images [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--sync", dest="sync", type=intx, default=1,
|
||||
help="Set sync [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_noaa_apt_decoder, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, flip_images=options.flip_images, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, sync=options.sync, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,470 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: satnogs_reaktor_hello_world_fsk9600_decoder
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: FSK 9600 Decoder for the Reaktor-Hello-World satellite
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
import math
|
||||
from gnuradio import blocks
|
||||
from gnuradio import digital
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
from gnuradio.filter import pfb
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_reaktor_hello_world_fsk9600_decoder(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', baudrate=9600.0, bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "satnogs_reaktor_hello_world_fsk9600_decoder")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.baudrate = baudrate
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.variable_whitening_0 = variable_whitening_0 = satnogs.whitening_make(0x21, 0x1FF, 8)
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
self.variable_ieee802_15_4_variant_decoder_0 = variable_ieee802_15_4_variant_decoder_0 = satnogs.ieee802_15_4_variant_decoder_make([0x55, 0x55, 0x55, 0x55, 0x55], 2, [0x35, 0x2E, 0x35, 0x2E], 1, satnogs.crc.CRC16_IBM, variable_whitening_0, True, 256)
|
||||
self.decimation = decimation = satnogs.find_decimation(baudrate, 2, audio_samp_rate)
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(baudrate*decimation, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_json_converter_0 = satnogs.json_converter()
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_frame_decoder_0_0 = satnogs.frame_decoder(variable_ieee802_15_4_variant_decoder_0, 1 * 1)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, baudrate*decimation, 1)
|
||||
self.pfb_arb_resampler_xxx_1 = pfb.arb_resampler_fff(
|
||||
audio_samp_rate / (baudrate*decimation),
|
||||
taps=None,
|
||||
flt_size=32)
|
||||
self.pfb_arb_resampler_xxx_1.declare_sample_delay(0)
|
||||
self.low_pass_filter_0_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
baudrate*decimation,
|
||||
baudrate*1.25,
|
||||
baudrate / 2.0,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0 = filter.fir_filter_ccf(
|
||||
decimation // 2,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
baudrate*decimation,
|
||||
0.75 * baudrate,
|
||||
baudrate / 8.0,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff(2, 2 * math.pi / 100, 0.5, 0.5/8.0, 0.01)
|
||||
self.digital_binary_slicer_fb_0 = digital.binary_slicer_fb()
|
||||
self.dc_blocker_xx_0_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.dc_blocker_xx_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.blocks_vco_c_0 = blocks.vco_c(baudrate*decimation, -baudrate*decimation, 1.0)
|
||||
self.blocks_multiply_xx_0 = blocks.multiply_vcc(1)
|
||||
self.blocks_moving_average_xx_0 = blocks.moving_average_ff(1024, 1.0/1024.0, 4096, 1)
|
||||
self.blocks_delay_0 = blocks.delay(gr.sizeof_gr_complex*1, 1024//2)
|
||||
self.analog_quadrature_demod_cf_0_0_0_0 = analog.quadrature_demod_cf(1.0)
|
||||
self.analog_quadrature_demod_cf_0_0_0 = analog.quadrature_demod_cf(0.9)
|
||||
self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf(1.2)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_frame_file_sink_0_1_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.dc_blocker_xx_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0_0, 0), (self.pfb_arb_resampler_xxx_1, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0_0_0, 0), (self.blocks_moving_average_xx_0, 0))
|
||||
self.connect((self.blocks_delay_0, 0), (self.blocks_multiply_xx_0, 0))
|
||||
self.connect((self.blocks_moving_average_xx_0, 0), (self.blocks_vco_c_0, 0))
|
||||
self.connect((self.blocks_multiply_xx_0, 0), (self.low_pass_filter_0, 0))
|
||||
self.connect((self.blocks_vco_c_0, 0), (self.blocks_multiply_xx_0, 1))
|
||||
self.connect((self.dc_blocker_xx_0, 0), (self.digital_clock_recovery_mm_xx_0, 0))
|
||||
self.connect((self.dc_blocker_xx_0_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_frame_decoder_0_0, 0))
|
||||
self.connect((self.digital_clock_recovery_mm_xx_0, 0), (self.digital_binary_slicer_fb_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.analog_quadrature_demod_cf_0_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.analog_quadrature_demod_cf_0_0_0_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_1, 0), (self.dc_blocker_xx_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.analog_quadrature_demod_cf_0_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.blocks_delay_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.low_pass_filter_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_baudrate(self):
|
||||
return self.baudrate
|
||||
|
||||
def set_baudrate(self, baudrate):
|
||||
self.baudrate = baudrate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate))
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, 0.75 * self.baudrate, self.baudrate / 8.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, self.baudrate*1.25, self.baudrate / 2.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_1.set_taps(firdes.low_pass(1, 2 * self.baudrate, self.baudrate * 0.60, self.baudrate / 8.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_1.set_rate(self.audio_samp_rate / (self.baudrate*self.decimation))
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_variable_whitening_0(self):
|
||||
return self.variable_whitening_0
|
||||
|
||||
def set_variable_whitening_0(self, variable_whitening_0):
|
||||
self.variable_whitening_0 = variable_whitening_0
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate))
|
||||
self.pfb_arb_resampler_xxx_1.set_rate(self.audio_samp_rate / (self.baudrate*self.decimation))
|
||||
|
||||
def get_variable_ieee802_15_4_variant_decoder_0(self):
|
||||
return self.variable_ieee802_15_4_variant_decoder_0
|
||||
|
||||
def set_variable_ieee802_15_4_variant_decoder_0(self, variable_ieee802_15_4_variant_decoder_0):
|
||||
self.variable_ieee802_15_4_variant_decoder_0 = variable_ieee802_15_4_variant_decoder_0
|
||||
|
||||
def get_decimation(self):
|
||||
return self.decimation
|
||||
|
||||
def set_decimation(self, decimation):
|
||||
self.decimation = decimation
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, 0.75 * self.baudrate, self.baudrate / 8.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, self.baudrate*1.25, self.baudrate / 2.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_1.set_rate(self.audio_samp_rate / (self.baudrate*self.decimation))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'FSK 9600 Decoder for the Reaktor-Hello-World satellite'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--baudrate", dest="baudrate", type=eng_float, default="9.6k",
|
||||
help="Set baudrate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_reaktor_hello_world_fsk9600_decoder, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, baudrate=options.baudrate, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,532 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: AFSK1200 AX.25 decoder
|
||||
# Author: Manolis Surligas (surligas@gmail.com), Vardakis Giorgos (vardakis.grg@gmail.com)
|
||||
# Description: AFSK1200 AX.25 decoder
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
import math
|
||||
from gnuradio import blocks
|
||||
from gnuradio import digital
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_afsk1200_ax25(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, mark_frequency=2200.0, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', space_frequency=1200.0, udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "AFSK1200 AX.25 decoder ")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.mark_frequency = mark_frequency
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.space_frequency = space_frequency
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.variable_ax25_decoder_0_0 = variable_ax25_decoder_0_0 = satnogs.ax25_decoder_make('GND', 0, True, False, True, 512)
|
||||
self.variable_ax25_decoder_0 = variable_ax25_decoder_0 = satnogs.ax25_decoder_make('GND', 0, True, True, True, 512)
|
||||
self.max_modulation_freq = max_modulation_freq = 3000
|
||||
self.deviation = deviation = 5000
|
||||
self.baudrate = baudrate = 1200
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(audio_samp_rate, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_json_converter_0 = satnogs.json_converter()
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_frame_decoder_0_0_0 = satnogs.frame_decoder(variable_ax25_decoder_0_0, 1 * 1)
|
||||
self.satnogs_frame_decoder_0_0 = satnogs.frame_decoder(variable_ax25_decoder_0, 1 * 1)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, audio_samp_rate, 1)
|
||||
self.low_pass_filter_2_0 = filter.fir_filter_fff(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
baudrate*2,
|
||||
baudrate /2+ 500 /2,
|
||||
500,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_1 = filter.fir_filter_ccf(
|
||||
20,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
(mark_frequency - space_frequency)/2.0 + 250,
|
||||
500,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
(deviation+max_modulation_freq) * 1.25,
|
||||
3e3,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
deviation+max_modulation_freq,
|
||||
1000,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff((48e3/20)/baudrate, 2*math.pi/100.0, 0.5, 0.5/8.0, 0.01)
|
||||
self.digital_binary_slicer_fb_0 = digital.binary_slicer_fb()
|
||||
self.dc_blocker_xx_0_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.dc_blocker_xx_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.blocks_vco_c_0 = blocks.vco_c(audio_samp_rate, -audio_samp_rate, 1.0)
|
||||
self.blocks_rotator_cc_0 = blocks.rotator_cc(-2.0 * math.pi * ( ((1200 + 2200) / 2) / audio_samp_rate))
|
||||
self.blocks_multiply_xx_0_0 = blocks.multiply_vcc(1)
|
||||
self.blocks_moving_average_xx_0 = blocks.moving_average_ff(1024, 1.0/1024.0, 4096, 1)
|
||||
self.blocks_float_to_complex_0 = blocks.float_to_complex(1)
|
||||
self.blocks_delay_0 = blocks.delay(gr.sizeof_gr_complex*1, 1024//2)
|
||||
self.band_pass_filter_0 = filter.fir_filter_fff(
|
||||
1,
|
||||
firdes.band_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
1000,
|
||||
2400,
|
||||
400,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.analog_quadrature_demod_cf_0_0_0_0 = analog.quadrature_demod_cf(1.0)
|
||||
self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf((2*math.pi*deviation)/audio_samp_rate)
|
||||
self.analog_quadrature_demod_cf_0 = analog.quadrature_demod_cf(((audio_samp_rate/20) / baudrate)/(math.pi*1))
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_frame_file_sink_0_1_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_quadrature_demod_cf_0, 0), (self.dc_blocker_xx_0_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.band_pass_filter_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0_0_0, 0), (self.blocks_moving_average_xx_0, 0))
|
||||
self.connect((self.band_pass_filter_0, 0), (self.dc_blocker_xx_0, 0))
|
||||
self.connect((self.blocks_delay_0, 0), (self.blocks_multiply_xx_0_0, 0))
|
||||
self.connect((self.blocks_float_to_complex_0, 0), (self.blocks_rotator_cc_0, 0))
|
||||
self.connect((self.blocks_moving_average_xx_0, 0), (self.blocks_vco_c_0, 0))
|
||||
self.connect((self.blocks_multiply_xx_0_0, 0), (self.low_pass_filter_0, 0))
|
||||
self.connect((self.blocks_rotator_cc_0, 0), (self.low_pass_filter_1, 0))
|
||||
self.connect((self.blocks_vco_c_0, 0), (self.blocks_multiply_xx_0_0, 1))
|
||||
self.connect((self.dc_blocker_xx_0, 0), (self.blocks_float_to_complex_0, 0))
|
||||
self.connect((self.dc_blocker_xx_0_0, 0), (self.low_pass_filter_2_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_frame_decoder_0_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_frame_decoder_0_0_0, 0))
|
||||
self.connect((self.digital_clock_recovery_mm_xx_0, 0), (self.digital_binary_slicer_fb_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.analog_quadrature_demod_cf_0_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.analog_quadrature_demod_cf_0_0_0_0, 0))
|
||||
self.connect((self.low_pass_filter_1, 0), (self.analog_quadrature_demod_cf_0, 0))
|
||||
self.connect((self.low_pass_filter_2_0, 0), (self.digital_clock_recovery_mm_xx_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.blocks_delay_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.low_pass_filter_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_mark_frequency(self):
|
||||
return self.mark_frequency
|
||||
|
||||
def set_mark_frequency(self, mark_frequency):
|
||||
self.mark_frequency = mark_frequency
|
||||
self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate, (self.mark_frequency - self.space_frequency)/2.0 + 250, 500, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_space_frequency(self):
|
||||
return self.space_frequency
|
||||
|
||||
def set_space_frequency(self, space_frequency):
|
||||
self.space_frequency = space_frequency
|
||||
self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate, (self.mark_frequency - self.space_frequency)/2.0 + 250, 500, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_variable_ax25_decoder_0_0(self):
|
||||
return self.variable_ax25_decoder_0_0
|
||||
|
||||
def set_variable_ax25_decoder_0_0(self, variable_ax25_decoder_0_0):
|
||||
self.variable_ax25_decoder_0_0 = variable_ax25_decoder_0_0
|
||||
|
||||
def get_variable_ax25_decoder_0(self):
|
||||
return self.variable_ax25_decoder_0
|
||||
|
||||
def set_variable_ax25_decoder_0(self, variable_ax25_decoder_0):
|
||||
self.variable_ax25_decoder_0 = variable_ax25_decoder_0
|
||||
|
||||
def get_max_modulation_freq(self):
|
||||
return self.max_modulation_freq
|
||||
|
||||
def set_max_modulation_freq(self, max_modulation_freq):
|
||||
self.max_modulation_freq = max_modulation_freq
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 1000, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, (self.deviation+self.max_modulation_freq) * 1.25, 3e3, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_deviation(self):
|
||||
return self.deviation
|
||||
|
||||
def set_deviation(self, deviation):
|
||||
self.deviation = deviation
|
||||
self.analog_quadrature_demod_cf_0_0.set_gain((2*math.pi*self.deviation)/self.audio_samp_rate)
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 1000, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, (self.deviation+self.max_modulation_freq) * 1.25, 3e3, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_baudrate(self):
|
||||
return self.baudrate
|
||||
|
||||
def set_baudrate(self, baudrate):
|
||||
self.baudrate = baudrate
|
||||
self.analog_quadrature_demod_cf_0.set_gain(((self.audio_samp_rate/20) / self.baudrate)/(math.pi*1))
|
||||
self.digital_clock_recovery_mm_xx_0.set_omega((48e3/20)/self.baudrate)
|
||||
self.low_pass_filter_2_0.set_taps(firdes.low_pass(1, self.baudrate*2, self.baudrate /2+ 500 /2, 500, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.analog_quadrature_demod_cf_0.set_gain(((self.audio_samp_rate/20) / self.baudrate)/(math.pi*1))
|
||||
self.analog_quadrature_demod_cf_0_0.set_gain((2*math.pi*self.deviation)/self.audio_samp_rate)
|
||||
self.band_pass_filter_0.set_taps(firdes.band_pass(1, self.audio_samp_rate, 1000, 2400, 400, firdes.WIN_HAMMING, 6.76))
|
||||
self.blocks_rotator_cc_0.set_phase_inc(-2.0 * math.pi * ( ((1200 + 2200) / 2) / self.audio_samp_rate))
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, self.deviation+self.max_modulation_freq, 1000, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, (self.deviation+self.max_modulation_freq) * 1.25, 3e3, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_1.set_taps(firdes.low_pass(1, self.audio_samp_rate, (self.mark_frequency - self.space_frequency)/2.0 + 250, 500, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'AFSK1200 AX.25 decoder'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--mark-frequency", dest="mark_frequency", type=eng_float, default="2.2k",
|
||||
help="Set mark_frequency [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--space-frequency", dest="space_frequency", type=eng_float, default="1.2k",
|
||||
help="Set space_frequency [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_afsk1200_ax25, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, mark_frequency=options.mark_frequency, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, space_frequency=options.space_frequency, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,523 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: satnogs_bpsk_ax25
|
||||
# Author: Manolis Surligas (surligas@gmail.com), Patrick Dohmen (DL4PD)
|
||||
# Description: BPSK AX.25 decoder
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
from gnuradio import blocks
|
||||
from gnuradio import digital
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
from gnuradio.filter import pfb
|
||||
import math
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_bpsk_ax25(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', baudrate=9600.0, bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, excess_bw=0.35, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, max_cfo=1000.0, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "satnogs_bpsk_ax25")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.baudrate = baudrate
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.excess_bw = excess_bw
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.max_cfo = max_cfo
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.sps = sps = 4
|
||||
self.nfilts = nfilts = 32
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
self.variable_ax25_decoder_0_0 = variable_ax25_decoder_0_0 = satnogs.ax25_decoder_make('GND', 0, True, False, True, 512)
|
||||
self.variable_ax25_decoder_0 = variable_ax25_decoder_0 = satnogs.ax25_decoder_make('GND', 0, True, True, True, 512)
|
||||
self.rrc_taps = rrc_taps = firdes.root_raised_cosine(nfilts, nfilts, 1.0/float(sps), excess_bw, 11*sps*nfilts)
|
||||
self.decimation = decimation = satnogs.find_decimation(baudrate, 2, audio_samp_rate,sps)
|
||||
self.bpsk_constellation = bpsk_constellation = digital.constellation_bpsk().base()
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0_0 = satnogs.waterfall_sink(baudrate*decimation, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_json_converter_0 = satnogs.json_converter()
|
||||
self.satnogs_iq_sink_0_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_frame_decoder_0_0_0 = satnogs.frame_decoder(variable_ax25_decoder_0_0, 1 * 1)
|
||||
self.satnogs_frame_decoder_0_0 = satnogs.frame_decoder(variable_ax25_decoder_0, 1 * 1)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, baudrate*decimation, 1)
|
||||
self.pfb_arb_resampler_xxx_0 = pfb.arb_resampler_ccf(
|
||||
audio_samp_rate/(baudrate*decimation),
|
||||
taps=None,
|
||||
flt_size=32)
|
||||
self.pfb_arb_resampler_xxx_0.declare_sample_delay(0)
|
||||
self.low_pass_filter_0_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
((1.0 + excess_bw) * baudrate/2.0) + min(baudrate, abs(max_cfo)),
|
||||
baudrate / 10.0,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0 = filter.fir_filter_ccf(
|
||||
decimation // sps,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
baudrate*decimation,
|
||||
((1.0 + excess_bw) * baudrate/2.0) + min(baudrate, abs(max_cfo)),
|
||||
baudrate / 10.0,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.digital_pfb_clock_sync_xxx_0 = digital.pfb_clock_sync_ccf(sps, 2.0 * math.pi/100.0, rrc_taps, nfilts, nfilts/2, 1.5, 1)
|
||||
self.digital_costas_loop_cc_0_0 = digital.costas_loop_cc(2.0 * math.pi / 100.0, 2, True)
|
||||
self.digital_constellation_receiver_cb_0 = digital.constellation_receiver_cb(bpsk_constellation, 2.0 * math.pi/100.0, -0.25, 0.25)
|
||||
self.blocks_rotator_cc_0_0 = blocks.rotator_cc(2.0 * math.pi * (1200.0 / audio_samp_rate))
|
||||
self.blocks_complex_to_real_0 = blocks.complex_to_real(1)
|
||||
self.analog_agc2_xx_0_0 = analog.agc2_cc(0.01, 0.001, 0.015, 1.0)
|
||||
self.analog_agc2_xx_0_0.set_max_gain(65536)
|
||||
self.analog_agc2_xx_0 = analog.agc2_cc(1e-3, 1e-3, 0.5, 1.0)
|
||||
self.analog_agc2_xx_0.set_max_gain(65536)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_frame_file_sink_0_1_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_agc2_xx_0, 0), (self.low_pass_filter_0, 0))
|
||||
self.connect((self.analog_agc2_xx_0, 0), (self.pfb_arb_resampler_xxx_0, 0))
|
||||
self.connect((self.analog_agc2_xx_0_0, 0), (self.low_pass_filter_0_0, 0))
|
||||
self.connect((self.blocks_complex_to_real_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.blocks_rotator_cc_0_0, 0), (self.blocks_complex_to_real_0, 0))
|
||||
self.connect((self.digital_constellation_receiver_cb_0, 0), (self.satnogs_frame_decoder_0_0, 0))
|
||||
self.connect((self.digital_constellation_receiver_cb_0, 0), (self.satnogs_frame_decoder_0_0_0, 0))
|
||||
self.connect((self.digital_costas_loop_cc_0_0, 0), (self.digital_pfb_clock_sync_xxx_0, 0))
|
||||
self.connect((self.digital_pfb_clock_sync_xxx_0, 0), (self.digital_constellation_receiver_cb_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.digital_costas_loop_cc_0_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.blocks_rotator_cc_0_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_0, 0), (self.analog_agc2_xx_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.analog_agc2_xx_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_baudrate(self):
|
||||
return self.baudrate
|
||||
|
||||
def set_baudrate(self, baudrate):
|
||||
self.baudrate = baudrate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate,self.sps))
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.audio_samp_rate/(self.baudrate*self.decimation))
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_excess_bw(self):
|
||||
return self.excess_bw
|
||||
|
||||
def set_excess_bw(self, excess_bw):
|
||||
self.excess_bw = excess_bw
|
||||
self.set_rrc_taps(firdes.root_raised_cosine(self.nfilts, self.nfilts, 1.0/float(self.sps), self.excess_bw, 11*self.sps*self.nfilts))
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_max_cfo(self):
|
||||
return self.max_cfo
|
||||
|
||||
def set_max_cfo(self, max_cfo):
|
||||
self.max_cfo = max_cfo
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_sps(self):
|
||||
return self.sps
|
||||
|
||||
def set_sps(self, sps):
|
||||
self.sps = sps
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate,self.sps))
|
||||
self.set_rrc_taps(firdes.root_raised_cosine(self.nfilts, self.nfilts, 1.0/float(self.sps), self.excess_bw, 11*self.sps*self.nfilts))
|
||||
|
||||
def get_nfilts(self):
|
||||
return self.nfilts
|
||||
|
||||
def set_nfilts(self, nfilts):
|
||||
self.nfilts = nfilts
|
||||
self.set_rrc_taps(firdes.root_raised_cosine(self.nfilts, self.nfilts, 1.0/float(self.sps), self.excess_bw, 11*self.sps*self.nfilts))
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate,self.sps))
|
||||
self.blocks_rotator_cc_0_0.set_phase_inc(2.0 * math.pi * (1200.0 / self.audio_samp_rate))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.audio_samp_rate/(self.baudrate*self.decimation))
|
||||
|
||||
def get_variable_ax25_decoder_0_0(self):
|
||||
return self.variable_ax25_decoder_0_0
|
||||
|
||||
def set_variable_ax25_decoder_0_0(self, variable_ax25_decoder_0_0):
|
||||
self.variable_ax25_decoder_0_0 = variable_ax25_decoder_0_0
|
||||
|
||||
def get_variable_ax25_decoder_0(self):
|
||||
return self.variable_ax25_decoder_0
|
||||
|
||||
def set_variable_ax25_decoder_0(self, variable_ax25_decoder_0):
|
||||
self.variable_ax25_decoder_0 = variable_ax25_decoder_0
|
||||
|
||||
def get_rrc_taps(self):
|
||||
return self.rrc_taps
|
||||
|
||||
def set_rrc_taps(self, rrc_taps):
|
||||
self.rrc_taps = rrc_taps
|
||||
self.digital_pfb_clock_sync_xxx_0.update_taps(self.rrc_taps)
|
||||
|
||||
def get_decimation(self):
|
||||
return self.decimation
|
||||
|
||||
def set_decimation(self, decimation):
|
||||
self.decimation = decimation
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, ((1.0 + self.excess_bw) * self.baudrate/2.0) + min(self.baudrate, abs(self.max_cfo)), self.baudrate / 10.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.audio_samp_rate/(self.baudrate*self.decimation))
|
||||
|
||||
def get_bpsk_constellation(self):
|
||||
return self.bpsk_constellation
|
||||
|
||||
def set_bpsk_constellation(self, bpsk_constellation):
|
||||
self.bpsk_constellation = bpsk_constellation
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'BPSK AX.25 decoder'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--baudrate", dest="baudrate", type=eng_float, default="9.6k",
|
||||
help="Set baudrate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--excess-bw", dest="excess_bw", type=eng_float, default="350.0m",
|
||||
help="Set excess_bw [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--max-cfo", dest="max_cfo", type=eng_float, default="1.0k",
|
||||
help="Set max_cfo [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_bpsk_ax25, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, baudrate=options.baudrate, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, excess_bw=options.excess_bw, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, max_cfo=options.max_cfo, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,466 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: CW Decoder
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: A CW (Morse) Decoder
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
from gnuradio import blocks
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
import math
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_cw_decoder(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', bfo_freq=1e3, bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat', wpm=20):
|
||||
gr.top_block.__init__(self, "CW Decoder")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.bfo_freq = bfo_freq
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
self.wpm = wpm
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
self.dot_samples = dot_samples = int((1.2 / wpm) / (1.0 / (audio_samp_rate / 10.0)))
|
||||
self.dec = dec = 8
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(audio_samp_rate, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_morse_decoder_0 = satnogs.morse_decoder(ord('#'), 3)
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, audio_samp_rate, 1)
|
||||
self.satnogs_cw_to_symbol_1 = satnogs.cw_to_symbol(audio_samp_rate/10, 2.0, 0.9, wpm, dot_samples//dec)
|
||||
self.low_pass_filter_0_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate,
|
||||
3000,
|
||||
1e3,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
audio_samp_rate/10,
|
||||
200,
|
||||
0.1e3,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.fir_filter_xxx_0 = filter.fir_filter_ccc(1, [1.0] * int(dot_samples//dec))
|
||||
self.fir_filter_xxx_0.declare_sample_delay(0)
|
||||
self.blocks_rotator_cc_0_0 = blocks.rotator_cc(2.0 * math.pi * (bfo_freq / audio_samp_rate))
|
||||
self.blocks_multiply_conjugate_cc_0 = blocks.multiply_conjugate_cc(1)
|
||||
self.blocks_keep_one_in_n_0 = blocks.keep_one_in_n(gr.sizeof_gr_complex*1, 10)
|
||||
self.blocks_delay_0 = blocks.delay(gr.sizeof_gr_complex*1, int(dot_samples//dec))
|
||||
self.blocks_complex_to_real_0 = blocks.complex_to_real(1)
|
||||
self.blocks_complex_to_mag_0 = blocks.complex_to_mag(1)
|
||||
self.analog_pll_carriertracking_cc_0 = analog.pll_carriertracking_cc(2*math.pi/100, 2*math.pi*2500, -2*math.pi*2500)
|
||||
self.analog_agc2_xx_0_0 = analog.agc2_cc(0.01, 0.001, 0.015, 0.0)
|
||||
self.analog_agc2_xx_0_0.set_max_gain(65536)
|
||||
self.analog_agc2_xx_0 = analog.agc2_cc(1e-4, 1e-4, 1.0, 1.0)
|
||||
self.analog_agc2_xx_0.set_max_gain(65536)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_cw_to_symbol_1, 'out'), (self.satnogs_morse_decoder_0, 'in'))
|
||||
self.msg_connect((self.satnogs_morse_decoder_0, 'out'), (self.satnogs_frame_file_sink_0_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_morse_decoder_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_agc2_xx_0, 0), (self.low_pass_filter_0_0, 0))
|
||||
self.connect((self.analog_agc2_xx_0_0, 0), (self.blocks_rotator_cc_0_0, 0))
|
||||
self.connect((self.analog_pll_carriertracking_cc_0, 0), (self.low_pass_filter_0, 0))
|
||||
self.connect((self.blocks_complex_to_mag_0, 0), (self.satnogs_cw_to_symbol_1, 0))
|
||||
self.connect((self.blocks_complex_to_real_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.blocks_delay_0, 0), (self.blocks_multiply_conjugate_cc_0, 1))
|
||||
self.connect((self.blocks_keep_one_in_n_0, 0), (self.analog_pll_carriertracking_cc_0, 0))
|
||||
self.connect((self.blocks_multiply_conjugate_cc_0, 0), (self.fir_filter_xxx_0, 0))
|
||||
self.connect((self.blocks_rotator_cc_0_0, 0), (self.blocks_complex_to_real_0, 0))
|
||||
self.connect((self.fir_filter_xxx_0, 0), (self.blocks_complex_to_mag_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.blocks_delay_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.blocks_multiply_conjugate_cc_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.analog_agc2_xx_0_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.blocks_keep_one_in_n_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.analog_agc2_xx_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_bfo_freq(self):
|
||||
return self.bfo_freq
|
||||
|
||||
def set_bfo_freq(self, bfo_freq):
|
||||
self.bfo_freq = bfo_freq
|
||||
self.blocks_rotator_cc_0_0.set_phase_inc(2.0 * math.pi * (self.bfo_freq / self.audio_samp_rate))
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_wpm(self):
|
||||
return self.wpm
|
||||
|
||||
def set_wpm(self, wpm):
|
||||
self.wpm = wpm
|
||||
self.set_dot_samples(int((1.2 / self.wpm) / (1.0 / (self.audio_samp_rate / 10.0))))
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.set_dot_samples(int((1.2 / self.wpm) / (1.0 / (self.audio_samp_rate / 10.0))))
|
||||
self.blocks_rotator_cc_0_0.set_phase_inc(2.0 * math.pi * (self.bfo_freq / self.audio_samp_rate))
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.audio_samp_rate/10, 200, 0.1e3, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.audio_samp_rate, 3000, 1e3, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_dot_samples(self):
|
||||
return self.dot_samples
|
||||
|
||||
def set_dot_samples(self, dot_samples):
|
||||
self.dot_samples = dot_samples
|
||||
self.blocks_delay_0.set_dly(int(self.dot_samples//self.dec))
|
||||
self.fir_filter_xxx_0.set_taps([1.0] * int(self.dot_samples//self.dec))
|
||||
|
||||
def get_dec(self):
|
||||
return self.dec
|
||||
|
||||
def set_dec(self, dec):
|
||||
self.dec = dec
|
||||
self.blocks_delay_0.set_dly(int(self.dot_samples//self.dec))
|
||||
self.fir_filter_xxx_0.set_taps([1.0] * int(self.dot_samples//self.dec))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'A CW (Morse) Decoder'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bfo-freq", dest="bfo_freq", type=eng_float, default="1.0k",
|
||||
help="Set bfo_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--wpm", dest="wpm", type=intx, default=20,
|
||||
help="Set wpm [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_cw_decoder, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, bfo_freq=options.bfo_freq, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path, wpm=options.wpm)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,414 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: An example flowgraph
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: An example flowgraph that can be used as a base for decoding flowgraphs
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
import math
|
||||
from gnuradio import filter
|
||||
from gnuradio import gr
|
||||
from gnuradio.filter import firdes
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_example_flowgraph(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', baudrate=9600.0, bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args_0='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "An example flowgraph")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.baudrate = baudrate
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args_0 = dev_args_0
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
self.xlate_filter_taps = xlate_filter_taps = firdes.low_pass(1, samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76)
|
||||
self.filter_rate = filter_rate = 250000
|
||||
self.decimation = decimation = satnogs.find_decimation(baudrate, 2, audio_samp_rate)
|
||||
self.audio_samp_rate_0 = audio_samp_rate_0 = 48000
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str('dev_args')
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, 'dev_args', samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(baudrate*decimation, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, audio_samp_rate, 1)
|
||||
self.dc_blocker_xx_0_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.analog_quadrature_demod_cf_0_0_0 = analog.quadrature_demod_cf(0.9)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0_0, 0), (self.dc_blocker_xx_0_0, 0))
|
||||
self.connect((self.dc_blocker_xx_0_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.analog_quadrature_demod_cf_0_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_baudrate(self):
|
||||
return self.baudrate
|
||||
|
||||
def set_baudrate(self, baudrate):
|
||||
self.baudrate = baudrate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate))
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args_0(self):
|
||||
return self.dev_args_0
|
||||
|
||||
def set_dev_args_0(self, dev_args_0):
|
||||
self.dev_args_0 = dev_args_0
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.set_xlate_filter_taps(firdes.low_pass(1, self.samp_rate_rx, 125000, 25000, firdes.WIN_HAMMING, 6.76))
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate))
|
||||
|
||||
def get_xlate_filter_taps(self):
|
||||
return self.xlate_filter_taps
|
||||
|
||||
def set_xlate_filter_taps(self, xlate_filter_taps):
|
||||
self.xlate_filter_taps = xlate_filter_taps
|
||||
|
||||
def get_filter_rate(self):
|
||||
return self.filter_rate
|
||||
|
||||
def set_filter_rate(self, filter_rate):
|
||||
self.filter_rate = filter_rate
|
||||
|
||||
def get_decimation(self):
|
||||
return self.decimation
|
||||
|
||||
def set_decimation(self, decimation):
|
||||
self.decimation = decimation
|
||||
|
||||
def get_audio_samp_rate_0(self):
|
||||
return self.audio_samp_rate_0
|
||||
|
||||
def set_audio_samp_rate_0(self, audio_samp_rate_0):
|
||||
self.audio_samp_rate_0 = audio_samp_rate_0
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'An example flowgraph that can be used as a base for decoding flowgraphs'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--baudrate", dest="baudrate", type=eng_float, default="9.6k",
|
||||
help="Set baudrate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args-0", dest="dev_args_0", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_example_flowgraph, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, baudrate=options.baudrate, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args_0=options.dev_args_0, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,473 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: satnogs_fsk_ax25
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: Generic FSK/MSK AX.25 decoder
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import analog
|
||||
import math
|
||||
from gnuradio import blocks
|
||||
from gnuradio import digital
|
||||
from gnuradio import filter
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio import gr
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
from gnuradio.filter import pfb
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_fsk_ax25(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', baudrate=9600.0, bw=0.0, decoded_data_file_path='/tmp/.satnogs/data/data', dev_args='', doppler_correction_per_sec=20, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', udp_IP='127.0.0.1', udp_port=16887, waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "satnogs_fsk_ax25")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.baudrate = baudrate
|
||||
self.bw = bw
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.udp_IP = udp_IP
|
||||
self.udp_port = udp_port
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.audio_samp_rate = audio_samp_rate = 48000
|
||||
self.variable_ax25_decoder_0_0 = variable_ax25_decoder_0_0 = satnogs.ax25_decoder_make('GND', 0, True, False, True, 512)
|
||||
self.variable_ax25_decoder_0 = variable_ax25_decoder_0 = satnogs.ax25_decoder_make('GND', 0, True, True, True, 512)
|
||||
self.decimation = decimation = satnogs.find_decimation(baudrate, 2, audio_samp_rate)
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(baudrate*decimation, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(udp_IP, udp_port, 1500)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_ogg_encoder_0 = satnogs.ogg_encoder(file_path, audio_samp_rate, 1.0)
|
||||
self.satnogs_json_converter_0 = satnogs.json_converter()
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_frame_file_sink_0_1_0 = satnogs.frame_file_sink(decoded_data_file_path, 0)
|
||||
self.satnogs_frame_decoder_0_0_0 = satnogs.frame_decoder(variable_ax25_decoder_0_0, 1 * 1)
|
||||
self.satnogs_frame_decoder_0_0 = satnogs.frame_decoder(variable_ax25_decoder_0, 1 * 1)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, baudrate*decimation, 1)
|
||||
self.pfb_arb_resampler_xxx_1 = pfb.arb_resampler_fff(
|
||||
audio_samp_rate / (baudrate*decimation),
|
||||
taps=None,
|
||||
flt_size=32)
|
||||
self.pfb_arb_resampler_xxx_1.declare_sample_delay(0)
|
||||
self.low_pass_filter_0_0 = filter.fir_filter_ccf(
|
||||
1,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
baudrate*decimation,
|
||||
baudrate*1.25,
|
||||
baudrate / 2.0,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.low_pass_filter_0 = filter.fir_filter_ccf(
|
||||
decimation // 2,
|
||||
firdes.low_pass(
|
||||
1,
|
||||
baudrate*decimation,
|
||||
0.75 * baudrate,
|
||||
baudrate / 8.0,
|
||||
firdes.WIN_HAMMING,
|
||||
6.76))
|
||||
self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff(2, 2 * math.pi / 100, 0.5, 0.5/8.0, 0.01)
|
||||
self.digital_binary_slicer_fb_0 = digital.binary_slicer_fb()
|
||||
self.dc_blocker_xx_0_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.dc_blocker_xx_0 = filter.dc_blocker_ff(1024, True)
|
||||
self.blocks_vco_c_0 = blocks.vco_c(baudrate*decimation, -baudrate*decimation, 1.0)
|
||||
self.blocks_multiply_xx_0 = blocks.multiply_vcc(1)
|
||||
self.blocks_moving_average_xx_0 = blocks.moving_average_ff(1024, 1.0/1024.0, 4096, 1)
|
||||
self.blocks_delay_0 = blocks.delay(gr.sizeof_gr_complex*1, 1024//2)
|
||||
self.analog_quadrature_demod_cf_0_0_0_0 = analog.quadrature_demod_cf(1.0)
|
||||
self.analog_quadrature_demod_cf_0_0_0 = analog.quadrature_demod_cf(0.9)
|
||||
self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf(1.2)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_frame_decoder_0_0_0, 'out'), (self.satnogs_json_converter_0, 'in'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_frame_file_sink_0_1_0, 'frame'))
|
||||
self.msg_connect((self.satnogs_json_converter_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.dc_blocker_xx_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0_0, 0), (self.pfb_arb_resampler_xxx_1, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0_0_0, 0), (self.blocks_moving_average_xx_0, 0))
|
||||
self.connect((self.blocks_delay_0, 0), (self.blocks_multiply_xx_0, 0))
|
||||
self.connect((self.blocks_moving_average_xx_0, 0), (self.blocks_vco_c_0, 0))
|
||||
self.connect((self.blocks_multiply_xx_0, 0), (self.low_pass_filter_0, 0))
|
||||
self.connect((self.blocks_vco_c_0, 0), (self.blocks_multiply_xx_0, 1))
|
||||
self.connect((self.dc_blocker_xx_0, 0), (self.digital_clock_recovery_mm_xx_0, 0))
|
||||
self.connect((self.dc_blocker_xx_0_0, 0), (self.satnogs_ogg_encoder_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_frame_decoder_0_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_frame_decoder_0_0_0, 0))
|
||||
self.connect((self.digital_clock_recovery_mm_xx_0, 0), (self.digital_binary_slicer_fb_0, 0))
|
||||
self.connect((self.low_pass_filter_0, 0), (self.analog_quadrature_demod_cf_0_0, 0))
|
||||
self.connect((self.low_pass_filter_0_0, 0), (self.analog_quadrature_demod_cf_0_0_0_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_1, 0), (self.dc_blocker_xx_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.analog_quadrature_demod_cf_0_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.blocks_delay_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.low_pass_filter_0_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_baudrate(self):
|
||||
return self.baudrate
|
||||
|
||||
def set_baudrate(self, baudrate):
|
||||
self.baudrate = baudrate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate))
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, 0.75 * self.baudrate, self.baudrate / 8.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, self.baudrate*1.25, self.baudrate / 2.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_1.set_taps(firdes.low_pass(1, 2 * self.baudrate, self.baudrate * 0.60, self.baudrate / 8.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_1.set_rate(self.audio_samp_rate / (self.baudrate*self.decimation))
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_decoded_data_file_path(self):
|
||||
return self.decoded_data_file_path
|
||||
|
||||
def set_decoded_data_file_path(self, decoded_data_file_path):
|
||||
self.decoded_data_file_path = decoded_data_file_path
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_udp_IP(self):
|
||||
return self.udp_IP
|
||||
|
||||
def set_udp_IP(self, udp_IP):
|
||||
self.udp_IP = udp_IP
|
||||
|
||||
def get_udp_port(self):
|
||||
return self.udp_port
|
||||
|
||||
def set_udp_port(self, udp_port):
|
||||
self.udp_port = udp_port
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
def get_audio_samp_rate(self):
|
||||
return self.audio_samp_rate
|
||||
|
||||
def set_audio_samp_rate(self, audio_samp_rate):
|
||||
self.audio_samp_rate = audio_samp_rate
|
||||
self.set_decimation(satnogs.find_decimation(self.baudrate, 2, self.audio_samp_rate))
|
||||
self.pfb_arb_resampler_xxx_1.set_rate(self.audio_samp_rate / (self.baudrate*self.decimation))
|
||||
|
||||
def get_variable_ax25_decoder_0_0(self):
|
||||
return self.variable_ax25_decoder_0_0
|
||||
|
||||
def set_variable_ax25_decoder_0_0(self, variable_ax25_decoder_0_0):
|
||||
self.variable_ax25_decoder_0_0 = variable_ax25_decoder_0_0
|
||||
|
||||
def get_variable_ax25_decoder_0(self):
|
||||
return self.variable_ax25_decoder_0
|
||||
|
||||
def set_variable_ax25_decoder_0(self, variable_ax25_decoder_0):
|
||||
self.variable_ax25_decoder_0 = variable_ax25_decoder_0
|
||||
|
||||
def get_decimation(self):
|
||||
return self.decimation
|
||||
|
||||
def set_decimation(self, decimation):
|
||||
self.decimation = decimation
|
||||
self.low_pass_filter_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, 0.75 * self.baudrate, self.baudrate / 8.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.low_pass_filter_0_0.set_taps(firdes.low_pass(1, self.baudrate*self.decimation, self.baudrate*1.25, self.baudrate / 2.0, firdes.WIN_HAMMING, 6.76))
|
||||
self.pfb_arb_resampler_xxx_1.set_rate(self.audio_samp_rate / (self.baudrate*self.decimation))
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'Generic FSK/MSK AX.25 decoder'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--baudrate", dest="baudrate", type=eng_float, default="9.6k",
|
||||
help="Set baudrate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--decoded-data-file-path", dest="decoded_data_file_path", type=str, default='/tmp/.satnogs/data/data',
|
||||
help="Set decoded_data_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-IP", dest="udp_IP", type=str, default='127.0.0.1',
|
||||
help="Set udp_IP [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--udp-port", dest="udp_port", type=intx, default=16887,
|
||||
help="Set udp_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_fsk_ax25, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, baudrate=options.baudrate, bw=options.bw, decoded_data_file_path=options.decoded_data_file_path, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, udp_IP=options.udp_IP, udp_port=options.udp_port, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
|
@ -1,344 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-3.0
|
||||
#
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: satnogs_iq_receiver
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: Generic IQ receiver with arbitrary output sampling rate
|
||||
# GNU Radio version: 3.8.0.0
|
||||
|
||||
from gnuradio import gr
|
||||
from gnuradio.filter import firdes
|
||||
import sys
|
||||
import signal
|
||||
from argparse import ArgumentParser
|
||||
from gnuradio.eng_arg import eng_float, intx
|
||||
from gnuradio import eng_notation
|
||||
import math
|
||||
import satnogs
|
||||
import soapy
|
||||
|
||||
class satnogs_iq_receiver(gr.top_block):
|
||||
|
||||
def __init__(self, antenna='', bw=0.0, dev_args='', doppler_correction_per_sec=20, enable_doppler_correction=1, enable_iq_dump=0, file_path='test.wav', gain=0.0, iq_file_path='/tmp/iq.dat', lo_offset=100e3, out_samp_rate=0.0, rigctl_port=4532, rx_freq=100e6, samp_rate_rx=0.0, soapy_rx_device='driver=invalid', waterfall_file_path='/tmp/waterfall.dat'):
|
||||
gr.top_block.__init__(self, "satnogs_iq_receiver")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.antenna = antenna
|
||||
self.bw = bw
|
||||
self.dev_args = dev_args
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
self.enable_doppler_correction = enable_doppler_correction
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
self.file_path = file_path
|
||||
self.gain = gain
|
||||
self.iq_file_path = iq_file_path
|
||||
self.lo_offset = lo_offset
|
||||
self.out_samp_rate = out_samp_rate
|
||||
self.rigctl_port = rigctl_port
|
||||
self.rx_freq = rx_freq
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.soapy_source_0 = None
|
||||
if "custom" == 'custom':
|
||||
dev = soapy_rx_device
|
||||
else:
|
||||
dev = 'driver=' + "custom"
|
||||
if "custom" == 'sdrplay':
|
||||
f = 'if_mode=' + "Zero-IF" + ',' + 'agc_setpoint=' + str("-30") + ',' + 'biasT_ctrl=' + "True".lower() + ',' + 'rfnotch_ctrl=' + "False".lower() + ',' + 'dabnotch_ctrl=' + "False".lower() + ',' + str(dev_args)
|
||||
f = f.replace('\"', '')
|
||||
f = f.replace("\\'", '')
|
||||
f = f.strip(',')
|
||||
self.soapy_source_0 = soapy.source(1, dev, f, samp_rate_rx, "fc32")
|
||||
else:
|
||||
self.soapy_source_0 = soapy.source(1, dev, dev_args, samp_rate_rx, "fc32")
|
||||
|
||||
if 0 != 0:
|
||||
self.soapy_source_0.set_master_clock_rate(0)
|
||||
|
||||
if len('') > 0:
|
||||
self.soapy_source_0.set_clock_source('')
|
||||
|
||||
# Set up dc offsets
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasDCOffset(0)):
|
||||
self.soapy_source_0.set_dc_offset(0,0,False == 'True')
|
||||
|
||||
if (self.soapy_source_0.hasDCOffset(1)):
|
||||
self.soapy_source_0.set_dc_offset(1,0,False == 'True')
|
||||
|
||||
# Setup IQ Balance
|
||||
if "custom" != 'uhd':
|
||||
if (self.soapy_source_0.hasIQBalance(0)):
|
||||
self.soapy_source_0.set_iq_balance(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasIQBalance(1)):
|
||||
self.soapy_source_0.set_iq_balance(1,0)
|
||||
|
||||
# Setup Frequency correction
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(0)):
|
||||
self.soapy_source_0.set_frequency_correction(0,0)
|
||||
|
||||
if (self.soapy_source_0.hasFrequencyCorrection(1)):
|
||||
self.soapy_source_0.set_frequency_correction(1,0)
|
||||
|
||||
self.soapy_source_0.set_gain_mode(0,False)
|
||||
self.soapy_source_0.set_gain_mode(1,False)
|
||||
|
||||
self.soapy_source_0.set_frequency(0, rx_freq - lo_offset)
|
||||
self.soapy_source_0.set_frequency(1, 0)
|
||||
|
||||
# Made antenna sanity check more generic
|
||||
antList = self.soapy_source_0.listAntennas(0)
|
||||
|
||||
if len(antList) > 1:
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antenna) == 0 or antenna not in antList:
|
||||
print("ERROR: Please define ant0 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(0,antenna)
|
||||
|
||||
if 1 > 1:
|
||||
antList = self.soapy_source_0.listAntennas(1)
|
||||
# If we have more than 1 possible antenna
|
||||
if len(antList) > 1:
|
||||
if len('RX2') == 0 or 'RX2' not in antList:
|
||||
print("ERROR: Please define ant1 to an allowed antenna name.")
|
||||
strAntList = str(antList).lstrip('(').rstrip(')').rstrip(',')
|
||||
print("Allowed antennas: " + strAntList)
|
||||
exit(0)
|
||||
|
||||
self.soapy_source_0.set_antenna(1,'RX2')
|
||||
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
# Prevent some weird double-gain setting issues for systems with an overall_gain setting
|
||||
# noticed weird behavior with uhd
|
||||
if "custom" == 'uhd' or "custom" == 'sidekiq' or "custom" == 'bladerf' or "custom" == 'lime':
|
||||
self.soapy_source_0.set_gain(0,"PGA", 24, False )
|
||||
self.soapy_source_0.set_gain(1,"PGA", 24, True )
|
||||
else:
|
||||
if "custom" == 'custom':
|
||||
# If we're here and we're custom, let's still call overall gain
|
||||
self.soapy_source_0.set_overall_gain(0,gain, False )
|
||||
self.soapy_source_0.set_overall_gain(1,10, True )
|
||||
|
||||
self.soapy_source_0.set_gain(0,"LNA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"LNA", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"TIA", 0, False )
|
||||
self.soapy_source_0.set_gain(1,"TIA", 0, True )
|
||||
self.soapy_source_0.set_gain(0,"MIX", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"MIX", 10, True )
|
||||
self.soapy_source_0.set_gain(0,"VGA", 10, False )
|
||||
self.soapy_source_0.set_gain(1,"VGA", 10, True )
|
||||
# Only rtl-sdr uses TUNER, so just ch0
|
||||
self.soapy_source_0.set_gain(0,"TUNER", 10, False )
|
||||
# Only hackrf uses "AMP", so just ch0
|
||||
self.soapy_source_0.set_gain(0,"AMP", 0, False )
|
||||
# Only sdrplay uses IFGR so just ch0 for each
|
||||
self.soapy_source_0.set_gain(0,"IFGR", 59, False )
|
||||
self.soapy_source_0.set_gain(0,"RFGR", 9, False )
|
||||
self.satnogs_waterfall_sink_0 = satnogs.waterfall_sink(out_samp_rate, rx_freq, 10, 1024, waterfall_file_path, 1)
|
||||
self.satnogs_tcp_rigctl_msg_source_0 = satnogs.tcp_rigctl_msg_source("127.0.0.1", rigctl_port, False, int(1000.0/doppler_correction_per_sec) + 1, 1500)
|
||||
self.satnogs_iq_sink_0 = satnogs.iq_sink(16768, iq_file_path, False, enable_iq_dump)
|
||||
self.satnogs_doppler_compensation_0 = satnogs.doppler_compensation(samp_rate_rx, rx_freq, lo_offset, out_samp_rate, enable_doppler_correction)
|
||||
|
||||
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_tcp_rigctl_msg_source_0, 'freq'), (self.satnogs_doppler_compensation_0, 'doppler'))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_iq_sink_0, 0))
|
||||
self.connect((self.satnogs_doppler_compensation_0, 0), (self.satnogs_waterfall_sink_0, 0))
|
||||
self.connect((self.soapy_source_0, 0), (self.satnogs_doppler_compensation_0, 0))
|
||||
|
||||
def get_antenna(self):
|
||||
return self.antenna
|
||||
|
||||
def set_antenna(self, antenna):
|
||||
self.antenna = antenna
|
||||
self.soapy_source_0.set_antenna(0,self.antenna)
|
||||
|
||||
def get_bw(self):
|
||||
return self.bw
|
||||
|
||||
def set_bw(self, bw):
|
||||
self.bw = bw
|
||||
self.soapy_source_0.set_bandwidth(0,self.bw)
|
||||
|
||||
def get_dev_args(self):
|
||||
return self.dev_args
|
||||
|
||||
def set_dev_args(self, dev_args):
|
||||
self.dev_args = dev_args
|
||||
|
||||
def get_doppler_correction_per_sec(self):
|
||||
return self.doppler_correction_per_sec
|
||||
|
||||
def set_doppler_correction_per_sec(self, doppler_correction_per_sec):
|
||||
self.doppler_correction_per_sec = doppler_correction_per_sec
|
||||
|
||||
def get_enable_doppler_correction(self):
|
||||
return self.enable_doppler_correction
|
||||
|
||||
def set_enable_doppler_correction(self, enable_doppler_correction):
|
||||
self.enable_doppler_correction = enable_doppler_correction
|
||||
|
||||
def get_enable_iq_dump(self):
|
||||
return self.enable_iq_dump
|
||||
|
||||
def set_enable_iq_dump(self, enable_iq_dump):
|
||||
self.enable_iq_dump = enable_iq_dump
|
||||
|
||||
def get_file_path(self):
|
||||
return self.file_path
|
||||
|
||||
def set_file_path(self, file_path):
|
||||
self.file_path = file_path
|
||||
|
||||
def get_gain(self):
|
||||
return self.gain
|
||||
|
||||
def set_gain(self, gain):
|
||||
self.gain = gain
|
||||
self.soapy_source_0.set_overall_gain(0,self.gain, False )
|
||||
|
||||
def get_iq_file_path(self):
|
||||
return self.iq_file_path
|
||||
|
||||
def set_iq_file_path(self, iq_file_path):
|
||||
self.iq_file_path = iq_file_path
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_out_samp_rate(self):
|
||||
return self.out_samp_rate
|
||||
|
||||
def set_out_samp_rate(self, out_samp_rate):
|
||||
self.out_samp_rate = out_samp_rate
|
||||
|
||||
def get_rigctl_port(self):
|
||||
return self.rigctl_port
|
||||
|
||||
def set_rigctl_port(self, rigctl_port):
|
||||
self.rigctl_port = rigctl_port
|
||||
|
||||
def get_rx_freq(self):
|
||||
return self.rx_freq
|
||||
|
||||
def set_rx_freq(self, rx_freq):
|
||||
self.rx_freq = rx_freq
|
||||
self.soapy_source_0.set_frequency(0, self.rx_freq - self.lo_offset)
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
|
||||
def get_soapy_rx_device(self):
|
||||
return self.soapy_rx_device
|
||||
|
||||
def set_soapy_rx_device(self, soapy_rx_device):
|
||||
self.soapy_rx_device = soapy_rx_device
|
||||
|
||||
def get_waterfall_file_path(self):
|
||||
return self.waterfall_file_path
|
||||
|
||||
def set_waterfall_file_path(self, waterfall_file_path):
|
||||
self.waterfall_file_path = waterfall_file_path
|
||||
|
||||
|
||||
def argument_parser():
|
||||
description = 'Generic IQ receiver with arbitrary output sampling rate'
|
||||
parser = ArgumentParser(description=description)
|
||||
parser.add_argument(
|
||||
"--antenna", dest="antenna", type=str, default='',
|
||||
help="Set antenna [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--bw", dest="bw", type=eng_float, default="0.0",
|
||||
help="Set Bandwidth [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--dev-args", dest="dev_args", type=str, default='',
|
||||
help="Set Device arguments [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--doppler-correction-per-sec", dest="doppler_correction_per_sec", type=intx, default=20,
|
||||
help="Set doppler_correction_per_sec [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-doppler-correction", dest="enable_doppler_correction", type=intx, default=1,
|
||||
help="Set enable_doppler_correction [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--enable-iq-dump", dest="enable_iq_dump", type=intx, default=0,
|
||||
help="Set enable_iq_dump [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--file-path", dest="file_path", type=str, default='test.wav',
|
||||
help="Set file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--gain", dest="gain", type=eng_float, default="0.0",
|
||||
help="Set gain [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--iq-file-path", dest="iq_file_path", type=str, default='/tmp/iq.dat',
|
||||
help="Set iq_file_path [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--lo-offset", dest="lo_offset", type=eng_float, default="100.0k",
|
||||
help="Set lo_offset [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--out-samp-rate", dest="out_samp_rate", type=eng_float, default="0.0",
|
||||
help="Set Output sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rigctl-port", dest="rigctl_port", type=intx, default=4532,
|
||||
help="Set rigctl_port [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--rx-freq", dest="rx_freq", type=eng_float, default="100.0M",
|
||||
help="Set rx_freq [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--samp-rate-rx", dest="samp_rate_rx", type=eng_float, default="0.0",
|
||||
help="Set Device Sampling rate [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--soapy-rx-device", dest="soapy_rx_device", type=str, default='driver=invalid',
|
||||
help="Set soapy_rx_device [default=%(default)r]")
|
||||
parser.add_argument(
|
||||
"--waterfall-file-path", dest="waterfall_file_path", type=str, default='/tmp/waterfall.dat',
|
||||
help="Set waterfall_file_path [default=%(default)r]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=satnogs_iq_receiver, options=None):
|
||||
if options is None:
|
||||
options = argument_parser().parse_args()
|
||||
tb = top_block_cls(antenna=options.antenna, bw=options.bw, dev_args=options.dev_args, doppler_correction_per_sec=options.doppler_correction_per_sec, enable_doppler_correction=options.enable_doppler_correction, enable_iq_dump=options.enable_iq_dump, file_path=options.file_path, gain=options.gain, iq_file_path=options.iq_file_path, lo_offset=options.lo_offset, out_samp_rate=options.out_samp_rate, rigctl_port=options.rigctl_port, rx_freq=options.rx_freq, samp_rate_rx=options.samp_rate_rx, soapy_rx_device=options.soapy_rx_device, waterfall_file_path=options.waterfall_file_path)
|
||||
|
||||
def sig_handler(sig=None, frame=None):
|
||||
tb.stop()
|
||||
tb.wait()
|
||||
sys.exit(0)
|
||||
|
||||
signal.signal(signal.SIGINT, sig_handler)
|
||||
signal.signal(signal.SIGTERM, sig_handler)
|
||||
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,363 @@
|
|||
#!/usr/bin/env python2
|
||||
# -*- coding: utf-8 -*-
|
||||
##################################################
|
||||
# GNU Radio Python Flow Graph
|
||||
# Title: Upsat Transceiver Cli
|
||||
# Author: Manolis Surligas (surligas@gmail.com)
|
||||
# Description: SATNOGS transceiver for UPSAT satellite
|
||||
# Generated: Sun Aug 14 22:13:27 2016
|
||||
##################################################
|
||||
|
||||
from gnuradio import analog
|
||||
from gnuradio import blocks
|
||||
from gnuradio import digital
|
||||
from gnuradio import eng_notation
|
||||
from gnuradio import filter
|
||||
from gnuradio import gr
|
||||
from gnuradio.eng_option import eng_option
|
||||
from gnuradio.filter import firdes
|
||||
from gnuradio.filter import pfb
|
||||
from optparse import OptionParser
|
||||
import math
|
||||
import numpy
|
||||
import osmosdr
|
||||
import satnogs
|
||||
import time
|
||||
|
||||
|
||||
class upsat_transceiver_cli(gr.top_block):
|
||||
|
||||
def __init__(self, bind_addr="0.0.0.0", dest_addr="127.0.0.1", lo_offset=100e3, recv_port=16886, rx_sdr_device="usrpb200", send_port=5022, tx_sdr_device="usrpb200", wod_port=5023):
|
||||
gr.top_block.__init__(self, "Upsat Transceiver Cli")
|
||||
|
||||
##################################################
|
||||
# Parameters
|
||||
##################################################
|
||||
self.bind_addr = bind_addr
|
||||
self.dest_addr = dest_addr
|
||||
self.lo_offset = lo_offset
|
||||
self.recv_port = recv_port
|
||||
self.rx_sdr_device = rx_sdr_device
|
||||
self.send_port = send_port
|
||||
self.tx_sdr_device = tx_sdr_device
|
||||
self.wod_port = wod_port
|
||||
|
||||
##################################################
|
||||
# Variables
|
||||
##################################################
|
||||
self.samples_per_symbol_tx = samples_per_symbol_tx = 4*8
|
||||
self.sq_wave = sq_wave = (1.0, ) * samples_per_symbol_tx
|
||||
self.samp_rate_rx = samp_rate_rx = satnogs.hw_rx_settings[rx_sdr_device]['samp_rate']
|
||||
self.gaussian_taps = gaussian_taps = filter.firdes.gaussian(1.0, samples_per_symbol_tx, 1.0, 4*samples_per_symbol_tx)
|
||||
self.deviation = deviation = 3.9973e3
|
||||
self.decimation_rx = decimation_rx = 20
|
||||
self.baud_rate_uplink = baud_rate_uplink = 1200
|
||||
self.baud_rate_downlink = baud_rate_downlink = 9600
|
||||
self.tx_frequency = tx_frequency = 145.835e6
|
||||
|
||||
self.taps = taps = firdes.low_pass(1.0, samp_rate_rx, 20000, 60000, firdes.WIN_HAMMING, 6.76)
|
||||
|
||||
self.samp_rate_tx = samp_rate_tx = satnogs.hw_tx_settings[rx_sdr_device]['samp_rate']
|
||||
self.rx_frequency = rx_frequency = 435.765e6
|
||||
self.modulation_index_uplink = modulation_index_uplink = deviation / (baud_rate_uplink / 2.0)
|
||||
self.modulation_index_downlink = modulation_index_downlink = deviation / (baud_rate_downlink / 2.0)
|
||||
self.interp_taps = interp_taps = numpy.convolve(numpy.array(gaussian_taps), numpy.array(sq_wave))
|
||||
self.first_stage_samp_rate_rx = first_stage_samp_rate_rx = samp_rate_rx / decimation_rx
|
||||
|
||||
##################################################
|
||||
# Blocks
|
||||
##################################################
|
||||
self.satnogs_upsat_fsk_frame_encoder_0 = satnogs.upsat_fsk_frame_encoder([0x33]*8 , [0x7A, 0x0E], False, False, False, True, True, "ABCD", 0, "ON02GR", 0, 64)
|
||||
self.satnogs_udp_msg_source_0 = satnogs.udp_msg_source(bind_addr, recv_port, 1500)
|
||||
self.satnogs_udp_msg_sink_0_0_0 = satnogs.udp_msg_sink(dest_addr, wod_port, 1500)
|
||||
self.satnogs_udp_msg_sink_0_0 = satnogs.udp_msg_sink(dest_addr, send_port, 1500)
|
||||
self.satnogs_qb50_deframer_0 = satnogs.qb50_deframer(0xe)
|
||||
self.satnogs_multi_format_msg_sink_0 = satnogs.multi_format_msg_sink(1)
|
||||
self.satnogs_ax25_decoder_bm_0 = satnogs.ax25_decoder_bm('GND', 0, False, True, 256, 3)
|
||||
self.pfb_arb_resampler_xxx_0 = pfb.arb_resampler_ccf(
|
||||
samp_rate_tx / (baud_rate_uplink * samples_per_symbol_tx),
|
||||
taps=(firdes.low_pass_2(32, 32, 0.8, 0.1, 60)),
|
||||
flt_size=32)
|
||||
self.pfb_arb_resampler_xxx_0.declare_sample_delay(0)
|
||||
|
||||
self.osmosdr_source_0 = osmosdr.source( args="numchan=" + str(1) + " " + satnogs.hw_rx_settings[rx_sdr_device]['dev_arg'] )
|
||||
self.osmosdr_source_0.set_sample_rate(samp_rate_rx)
|
||||
self.osmosdr_source_0.set_center_freq(rx_frequency - lo_offset, 0)
|
||||
self.osmosdr_source_0.set_freq_corr(0, 0)
|
||||
self.osmosdr_source_0.set_dc_offset_mode(0, 0)
|
||||
self.osmosdr_source_0.set_iq_balance_mode(0, 0)
|
||||
self.osmosdr_source_0.set_gain_mode(False, 0)
|
||||
self.osmosdr_source_0.set_gain(satnogs.hw_rx_settings[rx_sdr_device]['rf_gain'], 0)
|
||||
self.osmosdr_source_0.set_if_gain(satnogs.hw_rx_settings[rx_sdr_device]['if_gain'], 0)
|
||||
self.osmosdr_source_0.set_bb_gain(satnogs.hw_rx_settings[rx_sdr_device]['bb_gain'], 0)
|
||||
self.osmosdr_source_0.set_antenna(satnogs.hw_rx_settings[rx_sdr_device]['antenna'], 0)
|
||||
self.osmosdr_source_0.set_bandwidth(samp_rate_rx, 0)
|
||||
|
||||
self.osmosdr_sink_0 = osmosdr.sink( args="numchan=" + str(1) + " " + satnogs.hw_tx_settings[rx_sdr_device]['dev_arg'] )
|
||||
self.osmosdr_sink_0.set_sample_rate(samp_rate_tx)
|
||||
self.osmosdr_sink_0.set_center_freq(tx_frequency - lo_offset, 0)
|
||||
self.osmosdr_sink_0.set_freq_corr(0, 0)
|
||||
self.osmosdr_sink_0.set_gain(satnogs.hw_tx_settings[tx_sdr_device]['rf_gain'], 0)
|
||||
self.osmosdr_sink_0.set_if_gain(satnogs.hw_tx_settings[tx_sdr_device]['if_gain'], 0)
|
||||
self.osmosdr_sink_0.set_bb_gain(satnogs.hw_tx_settings[tx_sdr_device]['bb_gain'], 0)
|
||||
self.osmosdr_sink_0.set_antenna(satnogs.hw_tx_settings[tx_sdr_device]['antenna'], 0)
|
||||
self.osmosdr_sink_0.set_bandwidth(samp_rate_tx, 0)
|
||||
|
||||
self.interp_fir_filter_xxx_0 = filter.interp_fir_filter_fff(samples_per_symbol_tx, (interp_taps))
|
||||
self.interp_fir_filter_xxx_0.declare_sample_delay(0)
|
||||
self.freq_xlating_fir_filter_xxx_0 = filter.freq_xlating_fir_filter_ccc(decimation_rx, (taps), lo_offset, samp_rate_rx)
|
||||
self.digital_clock_recovery_mm_xx_0 = digital.clock_recovery_mm_ff(first_stage_samp_rate_rx/baud_rate_downlink, 0.25*0.175*0.175, 0.5, 0.175, 0.005)
|
||||
self.digital_binary_slicer_fb_0 = digital.binary_slicer_fb()
|
||||
self.blocks_multiply_xx_0 = blocks.multiply_vcc(1)
|
||||
self.analog_sig_source_x_0 = analog.sig_source_c(samp_rate_tx, analog.GR_COS_WAVE, lo_offset , 1, 0)
|
||||
self.analog_quadrature_demod_cf_0_0 = analog.quadrature_demod_cf(((first_stage_samp_rate_rx) / baud_rate_downlink)/(math.pi*modulation_index_downlink))
|
||||
self.analog_frequency_modulator_fc_0 = analog.frequency_modulator_fc((math.pi*modulation_index_uplink) / samples_per_symbol_tx)
|
||||
|
||||
##################################################
|
||||
# Connections
|
||||
##################################################
|
||||
self.msg_connect((self.satnogs_ax25_decoder_bm_0, 'failed_pdu'), (self.satnogs_multi_format_msg_sink_0, 'in'))
|
||||
self.msg_connect((self.satnogs_ax25_decoder_bm_0, 'pdu'), (self.satnogs_qb50_deframer_0, 'in'))
|
||||
self.msg_connect((self.satnogs_qb50_deframer_0, 'out'), (self.satnogs_udp_msg_sink_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_qb50_deframer_0, 'wod'), (self.satnogs_udp_msg_sink_0_0_0, 'in'))
|
||||
self.msg_connect((self.satnogs_udp_msg_source_0, 'msg'), (self.satnogs_upsat_fsk_frame_encoder_0, 'pdu'))
|
||||
self.connect((self.analog_frequency_modulator_fc_0, 0), (self.pfb_arb_resampler_xxx_0, 0))
|
||||
self.connect((self.analog_quadrature_demod_cf_0_0, 0), (self.digital_clock_recovery_mm_xx_0, 0))
|
||||
self.connect((self.analog_sig_source_x_0, 0), (self.blocks_multiply_xx_0, 1))
|
||||
self.connect((self.blocks_multiply_xx_0, 0), (self.osmosdr_sink_0, 0))
|
||||
self.connect((self.digital_binary_slicer_fb_0, 0), (self.satnogs_ax25_decoder_bm_0, 0))
|
||||
self.connect((self.digital_clock_recovery_mm_xx_0, 0), (self.digital_binary_slicer_fb_0, 0))
|
||||
self.connect((self.freq_xlating_fir_filter_xxx_0, 0), (self.analog_quadrature_demod_cf_0_0, 0))
|
||||
self.connect((self.interp_fir_filter_xxx_0, 0), (self.analog_frequency_modulator_fc_0, 0))
|
||||
self.connect((self.osmosdr_source_0, 0), (self.freq_xlating_fir_filter_xxx_0, 0))
|
||||
self.connect((self.pfb_arb_resampler_xxx_0, 0), (self.blocks_multiply_xx_0, 0))
|
||||
self.connect((self.satnogs_upsat_fsk_frame_encoder_0, 0), (self.interp_fir_filter_xxx_0, 0))
|
||||
|
||||
def get_bind_addr(self):
|
||||
return self.bind_addr
|
||||
|
||||
def set_bind_addr(self, bind_addr):
|
||||
self.bind_addr = bind_addr
|
||||
|
||||
def get_dest_addr(self):
|
||||
return self.dest_addr
|
||||
|
||||
def set_dest_addr(self, dest_addr):
|
||||
self.dest_addr = dest_addr
|
||||
|
||||
def get_lo_offset(self):
|
||||
return self.lo_offset
|
||||
|
||||
def set_lo_offset(self, lo_offset):
|
||||
self.lo_offset = lo_offset
|
||||
self.analog_sig_source_x_0.set_frequency(self.lo_offset )
|
||||
self.freq_xlating_fir_filter_xxx_0.set_center_freq(self.lo_offset)
|
||||
self.osmosdr_sink_0.set_center_freq(self.tx_frequency - self.lo_offset, 0)
|
||||
self.osmosdr_source_0.set_center_freq(self.rx_frequency - self.lo_offset, 0)
|
||||
|
||||
def get_recv_port(self):
|
||||
return self.recv_port
|
||||
|
||||
def set_recv_port(self, recv_port):
|
||||
self.recv_port = recv_port
|
||||
|
||||
def get_rx_sdr_device(self):
|
||||
return self.rx_sdr_device
|
||||
|
||||
def set_rx_sdr_device(self, rx_sdr_device):
|
||||
self.rx_sdr_device = rx_sdr_device
|
||||
self.set_samp_rate_rx(satnogs.hw_rx_settings[self.rx_sdr_device]['samp_rate'])
|
||||
self.set_samp_rate_tx(satnogs.hw_tx_settings[self.rx_sdr_device]['samp_rate'])
|
||||
self.osmosdr_source_0.set_gain(satnogs.hw_rx_settings[self.rx_sdr_device]['rf_gain'], 0)
|
||||
self.osmosdr_source_0.set_if_gain(satnogs.hw_rx_settings[self.rx_sdr_device]['if_gain'], 0)
|
||||
self.osmosdr_source_0.set_bb_gain(satnogs.hw_rx_settings[self.rx_sdr_device]['bb_gain'], 0)
|
||||
self.osmosdr_source_0.set_antenna(satnogs.hw_rx_settings[self.rx_sdr_device]['antenna'], 0)
|
||||
|
||||
def get_send_port(self):
|
||||
return self.send_port
|
||||
|
||||
def set_send_port(self, send_port):
|
||||
self.send_port = send_port
|
||||
|
||||
def get_tx_sdr_device(self):
|
||||
return self.tx_sdr_device
|
||||
|
||||
def set_tx_sdr_device(self, tx_sdr_device):
|
||||
self.tx_sdr_device = tx_sdr_device
|
||||
self.osmosdr_sink_0.set_gain(satnogs.hw_tx_settings[self.tx_sdr_device]['rf_gain'], 0)
|
||||
self.osmosdr_sink_0.set_if_gain(satnogs.hw_tx_settings[self.tx_sdr_device]['if_gain'], 0)
|
||||
self.osmosdr_sink_0.set_bb_gain(satnogs.hw_tx_settings[self.tx_sdr_device]['bb_gain'], 0)
|
||||
self.osmosdr_sink_0.set_antenna(satnogs.hw_tx_settings[self.tx_sdr_device]['antenna'], 0)
|
||||
|
||||
def get_wod_port(self):
|
||||
return self.wod_port
|
||||
|
||||
def set_wod_port(self, wod_port):
|
||||
self.wod_port = wod_port
|
||||
|
||||
def get_samples_per_symbol_tx(self):
|
||||
return self.samples_per_symbol_tx
|
||||
|
||||
def set_samples_per_symbol_tx(self, samples_per_symbol_tx):
|
||||
self.samples_per_symbol_tx = samples_per_symbol_tx
|
||||
self.set_gaussian_taps(filter.firdes.gaussian(1.0, self.samples_per_symbol_tx, 1.0, 4*self.samples_per_symbol_tx))
|
||||
self.set_sq_wave((1.0, ) * self.samples_per_symbol_tx)
|
||||
self.analog_frequency_modulator_fc_0.set_sensitivity((math.pi*self.modulation_index_uplink) / self.samples_per_symbol_tx)
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.samp_rate_tx / (self.baud_rate_uplink * self.samples_per_symbol_tx))
|
||||
|
||||
def get_sq_wave(self):
|
||||
return self.sq_wave
|
||||
|
||||
def set_sq_wave(self, sq_wave):
|
||||
self.sq_wave = sq_wave
|
||||
self.set_interp_taps(numpy.convolve(numpy.array(self.gaussian_taps), numpy.array(self.sq_wave)))
|
||||
|
||||
def get_samp_rate_rx(self):
|
||||
return self.samp_rate_rx
|
||||
|
||||
def set_samp_rate_rx(self, samp_rate_rx):
|
||||
self.samp_rate_rx = samp_rate_rx
|
||||
self.set_first_stage_samp_rate_rx(self.samp_rate_rx / self.decimation_rx)
|
||||
self.osmosdr_source_0.set_sample_rate(self.samp_rate_rx)
|
||||
self.osmosdr_source_0.set_bandwidth(self.samp_rate_rx, 0)
|
||||
|
||||
def get_gaussian_taps(self):
|
||||
return self.gaussian_taps
|
||||
|
||||
def set_gaussian_taps(self, gaussian_taps):
|
||||
self.gaussian_taps = gaussian_taps
|
||||
self.set_interp_taps(numpy.convolve(numpy.array(self.gaussian_taps), numpy.array(self.sq_wave)))
|
||||
|
||||
def get_deviation(self):
|
||||
return self.deviation
|
||||
|
||||
def set_deviation(self, deviation):
|
||||
self.deviation = deviation
|
||||
self.set_modulation_index_downlink(self.deviation / (self.baud_rate_downlink / 2.0))
|
||||
self.set_modulation_index_uplink(self.deviation / (self.baud_rate_uplink / 2.0))
|
||||
|
||||
def get_decimation_rx(self):
|
||||
return self.decimation_rx
|
||||
|
||||
def set_decimation_rx(self, decimation_rx):
|
||||
self.decimation_rx = decimation_rx
|
||||
self.set_first_stage_samp_rate_rx(self.samp_rate_rx / self.decimation_rx)
|
||||
|
||||
def get_baud_rate_uplink(self):
|
||||
return self.baud_rate_uplink
|
||||
|
||||
def set_baud_rate_uplink(self, baud_rate_uplink):
|
||||
self.baud_rate_uplink = baud_rate_uplink
|
||||
self.set_modulation_index_uplink(self.deviation / (self.baud_rate_uplink / 2.0))
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.samp_rate_tx / (self.baud_rate_uplink * self.samples_per_symbol_tx))
|
||||
|
||||
def get_baud_rate_downlink(self):
|
||||
return self.baud_rate_downlink
|
||||
|
||||
def set_baud_rate_downlink(self, baud_rate_downlink):
|
||||
self.baud_rate_downlink = baud_rate_downlink
|
||||
self.set_modulation_index_downlink(self.deviation / (self.baud_rate_downlink / 2.0))
|
||||
self.analog_quadrature_demod_cf_0_0.set_gain(((self.first_stage_samp_rate_rx) / self.baud_rate_downlink)/(math.pi*self.modulation_index_downlink))
|
||||
self.digital_clock_recovery_mm_xx_0.set_omega(self.first_stage_samp_rate_rx/self.baud_rate_downlink)
|
||||
|
||||
def get_tx_frequency(self):
|
||||
return self.tx_frequency
|
||||
|
||||
def set_tx_frequency(self, tx_frequency):
|
||||
self.tx_frequency = tx_frequency
|
||||
self.osmosdr_sink_0.set_center_freq(self.tx_frequency - self.lo_offset, 0)
|
||||
|
||||
def get_taps(self):
|
||||
return self.taps
|
||||
|
||||
def set_taps(self, taps):
|
||||
self.taps = taps
|
||||
self.freq_xlating_fir_filter_xxx_0.set_taps((self.taps))
|
||||
|
||||
def get_samp_rate_tx(self):
|
||||
return self.samp_rate_tx
|
||||
|
||||
def set_samp_rate_tx(self, samp_rate_tx):
|
||||
self.samp_rate_tx = samp_rate_tx
|
||||
self.analog_sig_source_x_0.set_sampling_freq(self.samp_rate_tx)
|
||||
self.osmosdr_sink_0.set_sample_rate(self.samp_rate_tx)
|
||||
self.osmosdr_sink_0.set_bandwidth(self.samp_rate_tx, 0)
|
||||
self.pfb_arb_resampler_xxx_0.set_rate(self.samp_rate_tx / (self.baud_rate_uplink * self.samples_per_symbol_tx))
|
||||
|
||||
def get_rx_frequency(self):
|
||||
return self.rx_frequency
|
||||
|
||||
def set_rx_frequency(self, rx_frequency):
|
||||
self.rx_frequency = rx_frequency
|
||||
self.osmosdr_source_0.set_center_freq(self.rx_frequency - self.lo_offset, 0)
|
||||
|
||||
def get_modulation_index_uplink(self):
|
||||
return self.modulation_index_uplink
|
||||
|
||||
def set_modulation_index_uplink(self, modulation_index_uplink):
|
||||
self.modulation_index_uplink = modulation_index_uplink
|
||||
self.analog_frequency_modulator_fc_0.set_sensitivity((math.pi*self.modulation_index_uplink) / self.samples_per_symbol_tx)
|
||||
|
||||
def get_modulation_index_downlink(self):
|
||||
return self.modulation_index_downlink
|
||||
|
||||
def set_modulation_index_downlink(self, modulation_index_downlink):
|
||||
self.modulation_index_downlink = modulation_index_downlink
|
||||
self.analog_quadrature_demod_cf_0_0.set_gain(((self.first_stage_samp_rate_rx) / self.baud_rate_downlink)/(math.pi*self.modulation_index_downlink))
|
||||
|
||||
def get_interp_taps(self):
|
||||
return self.interp_taps
|
||||
|
||||
def set_interp_taps(self, interp_taps):
|
||||
self.interp_taps = interp_taps
|
||||
self.interp_fir_filter_xxx_0.set_taps((self.interp_taps))
|
||||
|
||||
def get_first_stage_samp_rate_rx(self):
|
||||
return self.first_stage_samp_rate_rx
|
||||
|
||||
def set_first_stage_samp_rate_rx(self, first_stage_samp_rate_rx):
|
||||
self.first_stage_samp_rate_rx = first_stage_samp_rate_rx
|
||||
self.analog_quadrature_demod_cf_0_0.set_gain(((self.first_stage_samp_rate_rx) / self.baud_rate_downlink)/(math.pi*self.modulation_index_downlink))
|
||||
self.digital_clock_recovery_mm_xx_0.set_omega(self.first_stage_samp_rate_rx/self.baud_rate_downlink)
|
||||
|
||||
|
||||
def argument_parser():
|
||||
parser = OptionParser(option_class=eng_option, usage="%prog: [options]")
|
||||
parser.add_option(
|
||||
"", "--bind-addr", dest="bind_addr", type="string", default="0.0.0.0",
|
||||
help="Set bind_addr [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--dest-addr", dest="dest_addr", type="string", default="127.0.0.1",
|
||||
help="Set dest_addr [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--lo-offset", dest="lo_offset", type="eng_float", default=eng_notation.num_to_str(100e3),
|
||||
help="Set lo_offset [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--recv-port", dest="recv_port", type="intx", default=16886,
|
||||
help="Set recv_port [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--rx-sdr-device", dest="rx_sdr_device", type="string", default="usrpb200",
|
||||
help="Set rx_sdr_device [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--send-port", dest="send_port", type="intx", default=5022,
|
||||
help="Set send_port [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--tx-sdr-device", dest="tx_sdr_device", type="string", default="usrpb200",
|
||||
help="Set tx_sdr_device [default=%default]")
|
||||
parser.add_option(
|
||||
"", "--wod-port", dest="wod_port", type="intx", default=5023,
|
||||
help="Set wod_port [default=%default]")
|
||||
return parser
|
||||
|
||||
|
||||
def main(top_block_cls=upsat_transceiver_cli, options=None):
|
||||
if options is None:
|
||||
options, _ = argument_parser().parse_args()
|
||||
|
||||
tb = top_block_cls(bind_addr=options.bind_addr, dest_addr=options.dest_addr, lo_offset=options.lo_offset, recv_port=options.recv_port, rx_sdr_device=options.rx_sdr_device, send_port=options.send_port, tx_sdr_device=options.tx_sdr_device, wod_port=options.wod_port)
|
||||
tb.start()
|
||||
tb.wait()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
File diff suppressed because it is too large
Load Diff
|
@ -58,7 +58,7 @@
|
|||
# the new option.
|
||||
# E.g. my_install(TARGETS foo DESTINATION OPTIONAL) would result in
|
||||
# MY_INSTALL_DESTINATION set to "OPTIONAL", but MY_INSTALL_DESTINATION would
|
||||
# be empty and MY_INSTALL_OPTIONAL would be set to TRUE therefore.
|
||||
# be empty and MY_INSTALL_OPTIONAL would be set to TRUE therefor.
|
||||
|
||||
#=============================================================================
|
||||
# Copyright 2010 Alexander Neundorf <neundorf@kde.org>
|
||||
|
|
|
@ -1,332 +0,0 @@
|
|||
# Copyright (c) 2012 - 2017, Lars Bilke
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without modification,
|
||||
# are permitted provided that the following conditions are met:
|
||||
#
|
||||
# 1. Redistributions of source code must retain the above copyright notice, this
|
||||
# list of conditions and the following disclaimer.
|
||||
#
|
||||
# 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions and the following disclaimer in the documentation
|
||||
# and/or other materials provided with the distribution.
|
||||
#
|
||||
# 3. Neither the name of the copyright holder nor the names of its contributors
|
||||
# may be used to endorse or promote products derived from this software without
|
||||
# specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||
# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
#
|
||||
# CHANGES:
|
||||
#
|
||||
# 2012-01-31, Lars Bilke
|
||||
# - Enable Code Coverage
|
||||
#
|
||||
# 2013-09-17, Joakim Söderberg
|
||||
# - Added support for Clang.
|
||||
# - Some additional usage instructions.
|
||||
#
|
||||
# 2016-02-03, Lars Bilke
|
||||
# - Refactored functions to use named parameters
|
||||
#
|
||||
# 2017-06-02, Lars Bilke
|
||||
# - Merged with modified version from github.com/ufz/ogs
|
||||
#
|
||||
#
|
||||
# USAGE:
|
||||
#
|
||||
# 1. Copy this file into your cmake modules path.
|
||||
#
|
||||
# 2. Add the following line to your CMakeLists.txt:
|
||||
# include(CodeCoverage)
|
||||
#
|
||||
# 3. Append necessary compiler flags:
|
||||
# APPEND_COVERAGE_COMPILER_FLAGS()
|
||||
#
|
||||
# 3.a (OPTIONAL) Set appropriate optimization flags, e.g. -O0, -O1 or -Og
|
||||
#
|
||||
# 4. If you need to exclude additional directories from the report, specify them
|
||||
# using the COVERAGE_LCOV_EXCLUDES variable before calling SETUP_TARGET_FOR_COVERAGE_LCOV.
|
||||
# Example:
|
||||
# set(COVERAGE_LCOV_EXCLUDES 'dir1/*' 'dir2/*')
|
||||
#
|
||||
# 5. Use the functions described below to create a custom make target which
|
||||
# runs your test executable and produces a code coverage report.
|
||||
#
|
||||
# 6. Build a Debug build:
|
||||
# cmake -DCMAKE_BUILD_TYPE=Debug ..
|
||||
# make
|
||||
# make my_coverage_target
|
||||
#
|
||||
|
||||
include(CMakeParseArguments)
|
||||
|
||||
# Check prereqs
|
||||
find_program( GCOV_PATH gcov )
|
||||
find_program( LCOV_PATH NAMES lcov lcov.bat lcov.exe lcov.perl)
|
||||
find_program( GENHTML_PATH NAMES genhtml genhtml.perl genhtml.bat )
|
||||
find_program( GCOVR_PATH NAMES gcovr)
|
||||
find_program( PYTHON3_INTERP NAMES python3)
|
||||
|
||||
if(NOT PYTHON3_INTERP)
|
||||
message(FATAL_ERROR "python3 not found! Aborting...")
|
||||
endif()
|
||||
|
||||
if(NOT GCOV_PATH)
|
||||
message(FATAL_ERROR "gcov not found! Aborting...")
|
||||
endif() # NOT GCOV_PATH
|
||||
|
||||
if("${CMAKE_CXX_COMPILER_ID}" MATCHES "(Apple)?[Cc]lang")
|
||||
if("${CMAKE_CXX_COMPILER_VERSION}" VERSION_LESS 3)
|
||||
message(FATAL_ERROR "Clang version must be 3.0.0 or greater! Aborting...")
|
||||
endif()
|
||||
elseif(NOT CMAKE_COMPILER_IS_GNUCXX)
|
||||
message(FATAL_ERROR "Compiler is not GNU gcc! Aborting...")
|
||||
endif()
|
||||
|
||||
set(COVERAGE_COMPILER_FLAGS "-g --coverage -fprofile-arcs -ftest-coverage"
|
||||
CACHE INTERNAL "")
|
||||
|
||||
set(CMAKE_CXX_FLAGS_COVERAGE
|
||||
${COVERAGE_COMPILER_FLAGS}
|
||||
CACHE STRING "Flags used by the C++ compiler during coverage builds."
|
||||
FORCE )
|
||||
set(CMAKE_C_FLAGS_COVERAGE
|
||||
${COVERAGE_COMPILER_FLAGS}
|
||||
CACHE STRING "Flags used by the C compiler during coverage builds."
|
||||
FORCE )
|
||||
set(CMAKE_EXE_LINKER_FLAGS_COVERAGE
|
||||
""
|
||||
CACHE STRING "Flags used for linking binaries during coverage builds."
|
||||
FORCE )
|
||||
set(CMAKE_SHARED_LINKER_FLAGS_COVERAGE
|
||||
""
|
||||
CACHE STRING "Flags used by the shared libraries linker during coverage builds."
|
||||
FORCE )
|
||||
mark_as_advanced(
|
||||
CMAKE_CXX_FLAGS_COVERAGE
|
||||
CMAKE_C_FLAGS_COVERAGE
|
||||
CMAKE_EXE_LINKER_FLAGS_COVERAGE
|
||||
CMAKE_SHARED_LINKER_FLAGS_COVERAGE )
|
||||
|
||||
if(NOT CMAKE_BUILD_TYPE STREQUAL "Debug")
|
||||
message(WARNING "Code coverage results with an optimised (non-Debug) build may be misleading")
|
||||
endif() # NOT CMAKE_BUILD_TYPE STREQUAL "Debug"
|
||||
|
||||
if(CMAKE_C_COMPILER_ID STREQUAL "GNU")
|
||||
link_libraries(gcov)
|
||||
else()
|
||||
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} --coverage")
|
||||
endif()
|
||||
|
||||
###############################################################################
|
||||
# Handy macro to set easily a vatriable with a list of exclude directories
|
||||
###############################################################################
|
||||
macro(COVERAGE_SET_EXCLUDE_DIRS var)
|
||||
set(${var} ${ARGN} CACHE INTERNAL "" FORCE)
|
||||
endmacro(COVERAGE_SET_EXCLUDE_DIRS)
|
||||
|
||||
# Defines a target for running and collection code coverage information
|
||||
# Builds dependencies, runs the given executable and outputs reports.
|
||||
# NOTE! The executable should always have a ZERO as exit code otherwise
|
||||
# the coverage generation will not complete.
|
||||
#
|
||||
# SETUP_TARGET_FOR_COVERAGE_LCOV(
|
||||
# NAME testrunner_coverage # New target name
|
||||
# EXECUTABLE testrunner -j ${PROCESSOR_COUNT} # Executable in PROJECT_BINARY_DIR
|
||||
# DEPENDENCIES testrunner # Dependencies to build first
|
||||
# )
|
||||
function(SETUP_TARGET_FOR_COVERAGE_LCOV)
|
||||
|
||||
set(options NONE)
|
||||
set(oneValueArgs NAME)
|
||||
set(multiValueArgs EXECUTABLE EXECUTABLE_ARGS DEPENDENCIES LCOV_ARGS GENHTML_ARGS)
|
||||
cmake_parse_arguments(Coverage "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN})
|
||||
|
||||
if(NOT LCOV_PATH)
|
||||
message(FATAL_ERROR "lcov not found! Aborting...")
|
||||
endif() # NOT LCOV_PATH
|
||||
|
||||
if(NOT GENHTML_PATH)
|
||||
message(FATAL_ERROR "genhtml not found! Aborting...")
|
||||
endif() # NOT GENHTML_PATH
|
||||
|
||||
# Setup target
|
||||
add_custom_target(${Coverage_NAME}
|
||||
|
||||
# Cleanup lcov
|
||||
COMMAND ${LCOV_PATH} ${Coverage_LCOV_ARGS} --gcov-tool ${GCOV_PATH} -directory . --zerocounters
|
||||
# Create baseline to make sure untouched files show up in the report
|
||||
COMMAND ${LCOV_PATH} ${Coverage_LCOV_ARGS} --gcov-tool ${GCOV_PATH} -c -i -d . -o ${Coverage_NAME}.base
|
||||
|
||||
# Run tests
|
||||
COMMAND ${Coverage_EXECUTABLE} ${Coverage_EXECUTABLE_ARGS}
|
||||
|
||||
# Capturing lcov counters and generating report
|
||||
COMMAND ${LCOV_PATH} ${Coverage_LCOV_ARGS} --gcov-tool ${GCOV_PATH} --directory . --capture --output-file ${Coverage_NAME}.info
|
||||
# add baseline counters
|
||||
COMMAND ${LCOV_PATH} ${Coverage_LCOV_ARGS} --gcov-tool ${GCOV_PATH} -a ${Coverage_NAME}.base -a ${Coverage_NAME}.info --output-file ${Coverage_NAME}.total
|
||||
COMMAND ${LCOV_PATH} ${Coverage_LCOV_ARGS} --gcov-tool ${GCOV_PATH} --remove ${Coverage_NAME}.total ${COVERAGE_LCOV_EXCLUDES} --output-file ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info.cleaned
|
||||
COMMAND ${GENHTML_PATH} ${Coverage_GENHTML_ARGS} -o ${Coverage_NAME} ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info.cleaned
|
||||
COMMAND ${CMAKE_COMMAND} -E remove ${Coverage_NAME}.base ${Coverage_NAME}.total ${PROJECT_BINARY_DIR}/${Coverage_NAME}.info.cleaned
|
||||
|
||||
WORKING_DIRECTORY ${PROJECT_BINARY_DIR}
|
||||
DEPENDS ${Coverage_DEPENDENCIES}
|
||||
COMMENT "Resetting code coverage counters to zero.\nProcessing code coverage counters and generating report."
|
||||
)
|
||||
|
||||
# Show where to find the lcov info report
|
||||
add_custom_command(TARGET ${Coverage_NAME} POST_BUILD
|
||||
COMMAND ;
|
||||
COMMENT "Lcov code coverage info report saved in ${Coverage_NAME}.info."
|
||||
)
|
||||
|
||||
# Show info where to find the report
|
||||
add_custom_command(TARGET ${Coverage_NAME} POST_BUILD
|
||||
COMMAND ;
|
||||
COMMENT "Open ./${Coverage_NAME}/index.html in your browser to view the coverage report."
|
||||
)
|
||||
|
||||
endfunction() # SETUP_TARGET_FOR_COVERAGE_LCOV
|
||||
|
||||
# Defines a target for running and collection code coverage information
|
||||
# Builds dependencies, runs the given executable and outputs reports.
|
||||
# NOTE! The executable should always have a ZERO as exit code otherwise
|
||||
# the coverage generation will not complete.
|
||||
#
|
||||
# SETUP_TARGET_FOR_COVERAGE_GCOVR_XML(
|
||||
# NAME ctest_coverage # New target name
|
||||
# EXECUTABLE ctest -j ${PROCESSOR_COUNT} # Executable in PROJECT_BINARY_DIR
|
||||
# DEPENDENCIES executable_target # Dependencies to build first
|
||||
# )
|
||||
function(SETUP_TARGET_FOR_COVERAGE_GCOVR_XML)
|
||||
|
||||
set(options NONE)
|
||||
set(oneValueArgs NAME)
|
||||
set(multiValueArgs EXECUTABLE EXECUTABLE_ARGS DEPENDENCIES)
|
||||
cmake_parse_arguments(Coverage "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN})
|
||||
|
||||
if(NOT GCOVR_PATH)
|
||||
message(FATAL_ERROR "gcovr not found! Aborting...")
|
||||
endif() # NOT GCOVR_PATH
|
||||
|
||||
# Combine excludes to several -e arguments
|
||||
set(GCOVR_EXCLUDES "")
|
||||
set(GCOVR_EXCLUDES_DIRS "")
|
||||
foreach(EXCLUDE ${COVERAGE_GCOVR_EXCLUDES})
|
||||
string(REPLACE "*" "\\*" EXCLUDE_REPLACED ${EXCLUDE})
|
||||
list(APPEND GCOVR_EXCLUDES "-e")
|
||||
list(APPEND GCOVR_EXCLUDES "${EXCLUDE_REPLACED}")
|
||||
endforeach()
|
||||
foreach(EXCLUDE ${COVERAGE_GCOVR_EXCLUDE_DIRS})
|
||||
string(REPLACE "*" "\\*" EXCLUDE_REPLACED ${EXCLUDE})
|
||||
list(APPEND GCOVR_EXCLUDE_DIRS "--exclude-directories")
|
||||
list(APPEND GCOVR_EXCLUDE_DIRS "${EXCLUDE_REPLACED}")
|
||||
endforeach()
|
||||
|
||||
add_custom_target(${Coverage_NAME}
|
||||
# Run tests
|
||||
${Coverage_EXECUTABLE} ${Coverage_EXECUTABLE_ARGS}
|
||||
|
||||
# Running gcovr
|
||||
COMMAND ${GCOVR_PATH} --xml
|
||||
-r ${PROJECT_SOURCE_DIR} ${GCOVR_EXCLUDES} ${GCOVR_EXCLUDE_DIRS}
|
||||
--object-directory=${PROJECT_BINARY_DIR}
|
||||
-o ${Coverage_NAME}.xml
|
||||
WORKING_DIRECTORY ${PROJECT_BINARY_DIR}
|
||||
DEPENDS ${Coverage_DEPENDENCIES}
|
||||
COMMENT "Running gcovr to produce Cobertura code coverage report."
|
||||
)
|
||||
|
||||
# Show info where to find the report
|
||||
add_custom_command(TARGET ${Coverage_NAME} POST_BUILD
|
||||
COMMAND ;
|
||||
COMMENT "Cobertura code coverage report saved in ${Coverage_NAME}.xml."
|
||||
)
|
||||
|
||||
endfunction() # SETUP_TARGET_FOR_COVERAGE_GCOVR_XML
|
||||
|
||||
# Defines a target for running and collection code coverage information
|
||||
# Builds dependencies, runs the given executable and outputs reports.
|
||||
# NOTE! The executable should always have a ZERO as exit code otherwise
|
||||
# the coverage generation will not complete.
|
||||
#
|
||||
# SETUP_TARGET_FOR_COVERAGE_GCOVR_HTML(
|
||||
# NAME ctest_coverage # New target name
|
||||
# EXECUTABLE ctest -j ${PROCESSOR_COUNT} # Executable in PROJECT_BINARY_DIR
|
||||
# DEPENDENCIES executable_target # Dependencies to build first
|
||||
# )
|
||||
function(SETUP_TARGET_FOR_COVERAGE_GCOVR_HTML)
|
||||
|
||||
set(options NONE)
|
||||
set(oneValueArgs NAME)
|
||||
set(multiValueArgs EXECUTABLE EXECUTABLE_ARGS DEPENDENCIES)
|
||||
cmake_parse_arguments(Coverage "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN})
|
||||
|
||||
if(NOT GCOVR_PATH)
|
||||
message(FATAL_ERROR "gcovr not found! Aborting...")
|
||||
endif() # NOT GCOVR_PATH
|
||||
|
||||
# Combine excludes to several -e arguments
|
||||
set(GCOVR_EXCLUDES "")
|
||||
set(GCOVR_EXCLUDES_DIRS "")
|
||||
foreach(EXCLUDE ${COVERAGE_GCOVR_EXCLUDES})
|
||||
string(REPLACE "*" "\\*" EXCLUDE_REPLACED ${EXCLUDE})
|
||||
list(APPEND GCOVR_EXCLUDES "-e")
|
||||
list(APPEND GCOVR_EXCLUDES "${EXCLUDE_REPLACED}")
|
||||
endforeach()
|
||||
foreach(EXCLUDE ${COVERAGE_GCOVR_EXCLUDE_DIRS})
|
||||
string(REPLACE "*" "\\*" EXCLUDE_REPLACED ${EXCLUDE})
|
||||
list(APPEND GCOVR_EXCLUDE_DIRS "--exclude-directories")
|
||||
list(APPEND GCOVR_EXCLUDE_DIRS "${EXCLUDE_REPLACED}")
|
||||
endforeach()
|
||||
|
||||
add_custom_target(${Coverage_NAME}
|
||||
# Run tests
|
||||
${Coverage_EXECUTABLE} ${Coverage_EXECUTABLE_ARGS}
|
||||
|
||||
# Create folder
|
||||
COMMAND ${CMAKE_COMMAND} -E make_directory ${PROJECT_BINARY_DIR}/${Coverage_NAME}
|
||||
|
||||
# Running gcovr
|
||||
|
||||
COMMAND ${PYTHON3_INTERP} ${GCOVR_PATH} --html --html-details
|
||||
-r ${PROJECT_SOURCE_DIR} ${GCOVR_EXCLUDES} ${GCOVR_EXCLUDE_DIRS}
|
||||
--object-directory=${PROJECT_BINARY_DIR}
|
||||
-o ${Coverage_NAME}/index.html
|
||||
WORKING_DIRECTORY ${PROJECT_BINARY_DIR}
|
||||
DEPENDS ${Coverage_DEPENDENCIES}
|
||||
COMMENT "Running gcovr to produce HTML code coverage report."
|
||||
|
||||
# Run it again to generate the report in text based form for the
|
||||
# CI to parse it
|
||||
COMMAND ${PYTHON3_INTERP} ${GCOVR_PATH}
|
||||
-r ${PROJECT_SOURCE_DIR} ${GCOVR_EXCLUDES} ${GCOVR_EXCLUDE_DIRS}
|
||||
--object-directory=${PROJECT_BINARY_DIR}
|
||||
WORKING_DIRECTORY ${PROJECT_BINARY_DIR}
|
||||
DEPENDS ${Coverage_DEPENDENCIES}
|
||||
COMMENT "Running gcovr to produce HTML code coverage report."
|
||||
)
|
||||
|
||||
# Show info where to find the report
|
||||
add_custom_command(TARGET ${Coverage_NAME} POST_BUILD
|
||||
COMMAND ;
|
||||
COMMENT "Open ./${Coverage_NAME}/index.html in your browser to view the coverage report."
|
||||
)
|
||||
|
||||
endfunction() # SETUP_TARGET_FOR_COVERAGE_GCOVR_HTML
|
||||
|
||||
function(APPEND_COVERAGE_COMPILER_FLAGS)
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${COVERAGE_COMPILER_FLAGS}" PARENT_SCOPE)
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${COVERAGE_COMPILER_FLAGS}" PARENT_SCOPE)
|
||||
message(STATUS "Appending code coverage compiler flags: ${COVERAGE_COMPILER_FLAGS}")
|
||||
endfunction() # APPEND_COVERAGE_COMPILER_FLAGS
|
|
@ -0,0 +1,39 @@
|
|||
# http://www.cmake.org/pipermail/cmake/2006-October/011446.html
|
||||
# Modified to use pkg config and use standard var names
|
||||
|
||||
#
|
||||
# Find the CppUnit includes and library
|
||||
#
|
||||
# This module defines
|
||||
# CPPUNIT_INCLUDE_DIR, where to find tiff.h, etc.
|
||||
# CPPUNIT_LIBRARIES, the libraries to link against to use CppUnit.
|
||||
# CPPUNIT_FOUND, If false, do not try to use CppUnit.
|
||||
|
||||
INCLUDE(FindPkgConfig)
|
||||
PKG_CHECK_MODULES(PC_CPPUNIT "cppunit")
|
||||
|
||||
FIND_PATH(CPPUNIT_INCLUDE_DIRS
|
||||
NAMES cppunit/TestCase.h
|
||||
HINTS ${PC_CPPUNIT_INCLUDE_DIR}
|
||||
${CMAKE_INSTALL_PREFIX}/include
|
||||
PATHS
|
||||
/usr/local/include
|
||||
/usr/include
|
||||
)
|
||||
|
||||
FIND_LIBRARY(CPPUNIT_LIBRARIES
|
||||
NAMES cppunit
|
||||
HINTS ${PC_CPPUNIT_LIBDIR}
|
||||
${CMAKE_INSTALL_PREFIX}/lib
|
||||
${CMAKE_INSTALL_PREFIX}/lib64
|
||||
PATHS
|
||||
${CPPUNIT_INCLUDE_DIRS}/../lib
|
||||
/usr/local/lib
|
||||
/usr/lib
|
||||
)
|
||||
|
||||
LIST(APPEND CPPUNIT_LIBRARIES ${CMAKE_DL_LIBS})
|
||||
|
||||
INCLUDE(FindPackageHandleStandardArgs)
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS(CPPUNIT DEFAULT_MSG CPPUNIT_LIBRARIES CPPUNIT_INCLUDE_DIRS)
|
||||
MARK_AS_ADVANCED(CPPUNIT_LIBRARIES CPPUNIT_INCLUDE_DIRS)
|
|
@ -0,0 +1,36 @@
|
|||
INCLUDE(FindPkgConfig)
|
||||
PKG_CHECK_MODULES(PC_GNURADIO_RUNTIME gnuradio-runtime)
|
||||
|
||||
if(PC_GNURADIO_RUNTIME_FOUND)
|
||||
# look for include files
|
||||
FIND_PATH(
|
||||
GNURADIO_RUNTIME_INCLUDE_DIRS
|
||||
NAMES gnuradio/top_block.h
|
||||
HINTS $ENV{GNURADIO_RUNTIME_DIR}/include
|
||||
${PC_GNURADIO_RUNTIME_INCLUDE_DIRS}
|
||||
${CMAKE_INSTALL_PREFIX}/include
|
||||
PATHS /usr/local/include
|
||||
/usr/include
|
||||
)
|
||||
|
||||
# look for libs
|
||||
FIND_LIBRARY(
|
||||
GNURADIO_RUNTIME_LIBRARIES
|
||||
NAMES gnuradio-runtime
|
||||
HINTS $ENV{GNURADIO_RUNTIME_DIR}/lib
|
||||
${PC_GNURADIO_RUNTIME_LIBDIR}
|
||||
${CMAKE_INSTALL_PREFIX}/lib/
|
||||
${CMAKE_INSTALL_PREFIX}/lib64/
|
||||
PATHS /usr/local/lib
|
||||
/usr/local/lib64
|
||||
/usr/lib
|
||||
/usr/lib64
|
||||
)
|
||||
|
||||
set(GNURADIO_RUNTIME_FOUND ${PC_GNURADIO_RUNTIME_FOUND})
|
||||
endif(PC_GNURADIO_RUNTIME_FOUND)
|
||||
|
||||
INCLUDE(FindPackageHandleStandardArgs)
|
||||
# do not check GNURADIO_RUNTIME_INCLUDE_DIRS, is not set when default include path us used.
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS(GNURADIO_RUNTIME DEFAULT_MSG GNURADIO_RUNTIME_LIBRARIES)
|
||||
MARK_AS_ADVANCED(GNURADIO_RUNTIME_LIBRARIES GNURADIO_RUNTIME_INCLUDE_DIRS)
|
|
@ -1,392 +0,0 @@
|
|||
# - Find jsoncpp - Overarching find module
|
||||
# This is a over-arching find module to find older jsoncpp versions and those sadly built
|
||||
# without JSONCPP_WITH_CMAKE_PACKAGE=ON, as well as those built with the cmake config file.
|
||||
# It also wraps the different versions of the module.
|
||||
#
|
||||
# On CMake 3.0 and newer:
|
||||
# JsonCpp::JsonCpp - Imported target (possibly an interface/alias) to use:
|
||||
# if anything is populated, this is. If both shared and static are found, then
|
||||
# this will be the static version on DLL platforms and shared on non-DLL platforms.
|
||||
# JsonCpp::JsonCppShared - Imported target (possibly an interface/alias) for a
|
||||
# shared library version.
|
||||
# JsonCpp::JsonCppStatic - Imported target (possibly an interface/alias) for a
|
||||
# static library version.
|
||||
#
|
||||
# On all CMake versions: (Note that on CMake 2.8.10 and earlier, you may need to use JSONCPP_INCLUDE_DIRS)
|
||||
# JSONCPP_LIBRARY - wraps JsonCpp::JsonCpp or equiv.
|
||||
# JSONCPP_LIBRARY_IS_SHARED - if we know for sure JSONCPP_LIBRARY is shared, this is true-ish. We try to "un-set" it if we don't know one way or another.
|
||||
# JSONCPP_LIBRARY_SHARED - wraps JsonCpp::JsonCppShared or equiv.
|
||||
# JSONCPP_LIBRARY_STATIC - wraps JsonCpp::JsonCppStatic or equiv.
|
||||
# JSONCPP_INCLUDE_DIRS - Include directories - should (generally?) not needed if you require CMake 2.8.11+ since it handles target include directories.
|
||||
#
|
||||
# JSONCPP_FOUND - True if JsonCpp was found.
|
||||
#
|
||||
# Original Author:
|
||||
# 2016 Ryan Pavlik <ryan.pavlik@gmail.com>
|
||||
# Incorporates work from the module contributed to VRPN under the same license:
|
||||
# 2011 Philippe Crassous (ENSAM ParisTech / Institut Image) p.crassous _at_ free.fr
|
||||
#
|
||||
# Copyright Philippe Crassous 2011.
|
||||
# Copyright Sensics, Inc. 2016.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
|
||||
set(__jsoncpp_have_namespaced_targets OFF)
|
||||
set(__jsoncpp_have_interface_support OFF)
|
||||
if(NOT ("${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION}" LESS 3.0))
|
||||
set(__jsoncpp_have_namespaced_targets ON)
|
||||
set(__jsoncpp_have_interface_support ON)
|
||||
elseif(("${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION}" EQUAL 2.8) AND "${CMAKE_PATCH_VERSION}" GREATER 10)
|
||||
set(__jsoncpp_have_interface_support ON)
|
||||
endif()
|
||||
|
||||
# sets __jsoncpp_have_jsoncpplib based on whether or not we have a real imported jsoncpp_lib target.
|
||||
macro(_jsoncpp_check_for_real_jsoncpplib)
|
||||
set(__jsoncpp_have_jsoncpplib FALSE)
|
||||
if(TARGET jsoncpp_lib)
|
||||
get_property(__jsoncpp_lib_type TARGET jsoncpp_lib PROPERTY TYPE)
|
||||
# We make interface libraries. If an actual config module made it, it would be an imported library.
|
||||
if(NOT __jsoncpp_lib_type STREQUAL "INTERFACE_LIBRARY")
|
||||
set(__jsoncpp_have_jsoncpplib TRUE)
|
||||
endif()
|
||||
endif()
|
||||
#message(STATUS "__jsoncpp_have_jsoncpplib ${__jsoncpp_have_jsoncpplib}")
|
||||
endmacro()
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
# Ensure that if this is TRUE later, it's because we set it.
|
||||
set(JSONCPP_FOUND FALSE)
|
||||
set(__jsoncpp_have_jsoncpplib FALSE)
|
||||
|
||||
# See if we find a CMake config file - there is no harm in calling this more than once,
|
||||
# and we need to call it at least once every CMake invocation to create the original
|
||||
# imported targets, since those don't stick around like cache variables.
|
||||
find_package(jsoncpp QUIET NO_MODULE)
|
||||
|
||||
if(jsoncpp_FOUND)
|
||||
# Build a string to help us figure out when to invalidate our cache variables.
|
||||
# start with where we found jsoncpp
|
||||
set(__jsoncpp_info_string "[${jsoncpp_DIR}]")
|
||||
|
||||
# part of the string to indicate if we found a real jsoncpp_lib (and what kind)
|
||||
_jsoncpp_check_for_real_jsoncpplib()
|
||||
|
||||
macro(_jsoncpp_apply_map_config target)
|
||||
if(MSVC)
|
||||
# Can't do this - different runtimes, incompatible ABI, etc.
|
||||
set(_jsoncpp_debug_fallback)
|
||||
else()
|
||||
set(_jsoncpp_debug_fallback DEBUG)
|
||||
#osvr_stash_map_config(DEBUG DEBUG RELWITHDEBINFO RELEASE MINSIZEREL NONE)
|
||||
endif()
|
||||
# Appending, just in case using project or upstream fixes this.
|
||||
set_property(TARGET ${target} APPEND PROPERTY MAP_IMPORTED_CONFIG_RELEASE RELEASE RELWITHDEBINFO MINSIZEREL NONE ${_jsoncpp_debug_fallback})
|
||||
set_property(TARGET ${target} APPEND PROPERTY MAP_IMPORTED_CONFIG_RELWITHDEBINFO RELWITHDEBINFO RELEASE MINSIZEREL NONE ${_jsoncpp_debug_fallback})
|
||||
set_property(TARGET ${target} APPEND PROPERTY MAP_IMPORTED_CONFIG_MINSIZEREL MINSIZEREL RELEASE RELWITHDEBINFO NONE ${_jsoncpp_debug_fallback})
|
||||
set_property(TARGET ${target} APPEND PROPERTY MAP_IMPORTED_CONFIG_NONE NONE RELEASE RELWITHDEBINFO MINSIZEREL ${_jsoncpp_debug_fallback})
|
||||
if(NOT MSVC)
|
||||
set_property(TARGET ${target} APPEND PROPERTY MAP_IMPORTED_CONFIG_DEBUG DEBUG RELWITHDEBINFO RELEASE MINSIZEREL NONE)
|
||||
endif()
|
||||
endmacro()
|
||||
if(__jsoncpp_have_jsoncpplib)
|
||||
list(APPEND __jsoncpp_info_string "[${__jsoncpp_lib_type}]")
|
||||
_jsoncpp_apply_map_config(jsoncpp_lib)
|
||||
else()
|
||||
list(APPEND __jsoncpp_info_string "[]")
|
||||
endif()
|
||||
# part of the string to indicate if we found jsoncpp_lib_static
|
||||
if(TARGET jsoncpp_lib_static)
|
||||
list(APPEND __jsoncpp_info_string "[T]")
|
||||
_jsoncpp_apply_map_config(jsoncpp_lib_static)
|
||||
else()
|
||||
list(APPEND __jsoncpp_info_string "[]")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
|
||||
# If we found something, and it's not the exact same as what we've found before...
|
||||
# NOTE: The contents of this "if" block update only (internal) cache variables!
|
||||
# (since this will only get run the first CMake pass that finds jsoncpp or that finds a different/updated install)
|
||||
if(jsoncpp_FOUND AND NOT __jsoncpp_info_string STREQUAL "${JSONCPP_CACHED_JSONCPP_DIR_DETAILS}")
|
||||
#message("Updating jsoncpp cache variables! ${__jsoncpp_info_string}")
|
||||
set(JSONCPP_CACHED_JSONCPP_DIR_DETAILS "${__jsoncpp_info_string}" CACHE INTERNAL "" FORCE)
|
||||
unset(JSONCPP_IMPORTED_LIBRARY_SHARED)
|
||||
unset(JSONCPP_IMPORTED_LIBRARY_STATIC)
|
||||
unset(JSONCPP_IMPORTED_LIBRARY)
|
||||
unset(JSONCPP_IMPORTED_INCLUDE_DIRS)
|
||||
unset(JSONCPP_IMPORTED_LIBRARY_IS_SHARED)
|
||||
|
||||
# if(__jsoncpp_have_jsoncpplib) is equivalent to if(TARGET jsoncpp_lib) except it excludes our
|
||||
# "invented" jsoncpp_lib interface targets, made for convenience purposes after this block.
|
||||
|
||||
if(__jsoncpp_have_jsoncpplib AND TARGET jsoncpp_lib_static)
|
||||
|
||||
# A veritable cache of riches - we have both shared and static!
|
||||
set(JSONCPP_IMPORTED_LIBRARY_SHARED jsoncpp_lib CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY_STATIC jsoncpp_lib_static CACHE INTERNAL "" FORCE)
|
||||
if(WIN32 OR CYGWIN OR MINGW)
|
||||
# DLL platforms: static library should be default
|
||||
set(JSONCPP_IMPORTED_LIBRARY ${JSONCPP_IMPORTED_LIBRARY_STATIC} CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY_IS_SHARED FALSE CACHE INTERNAL "" FORCE)
|
||||
else()
|
||||
# Other platforms - might require PIC to be linked into shared libraries, so safest to prefer shared.
|
||||
set(JSONCPP_IMPORTED_LIBRARY ${JSONCPP_IMPORTED_LIBRARY_SHARED} CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY_IS_SHARED TRUE CACHE INTERNAL "" FORCE)
|
||||
endif()
|
||||
|
||||
elseif(TARGET jsoncpp_lib_static)
|
||||
# Well, only one variant, but we know for sure that it's static.
|
||||
set(JSONCPP_IMPORTED_LIBRARY_STATIC jsoncpp_lib_static CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY jsoncpp_lib_static CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY_IS_SHARED FALSE CACHE INTERNAL "" FORCE)
|
||||
|
||||
elseif(__jsoncpp_have_jsoncpplib AND __jsoncpp_lib_type STREQUAL "STATIC_LIBRARY")
|
||||
# We were able to figure out the mystery library is static!
|
||||
set(JSONCPP_IMPORTED_LIBRARY_STATIC jsoncpp_lib CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY jsoncpp_lib CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY_IS_SHARED FALSE CACHE INTERNAL "" FORCE)
|
||||
|
||||
elseif(__jsoncpp_have_jsoncpplib AND __jsoncpp_lib_type STREQUAL "SHARED_LIBRARY")
|
||||
# We were able to figure out the mystery library is shared!
|
||||
set(JSONCPP_IMPORTED_LIBRARY_SHARED jsoncpp_lib CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY jsoncpp_lib CACHE INTERNAL "" FORCE)
|
||||
set(JSONCPP_IMPORTED_LIBRARY_IS_SHARED TRUE CACHE INTERNAL "" FORCE)
|
||||
|
||||
elseif(__jsoncpp_have_jsoncpplib)
|
||||
# One variant, and we have no idea if this is just an old version or if
|
||||
# this is shared based on the target name alone. Hmm.
|
||||
set(JSONCPP_IMPORTED_LIBRARY jsoncpp_lib CACHE INTERNAL "" FORCE)
|
||||
endif()
|
||||
|
||||
# Now, we need include directories. Can't just limit this to old CMakes, since
|
||||
# new CMakes might be used to build projects designed to support older ones.
|
||||
if(__jsoncpp_have_jsoncpplib)
|
||||
get_property(__jsoncpp_interface_include_dirs TARGET jsoncpp_lib PROPERTY INTERFACE_INCLUDE_DIRECTORIES)
|
||||
if(__jsoncpp_interface_include_dirs)
|
||||
set(JSONCPP_IMPORTED_INCLUDE_DIRS "${__jsoncpp_interface_include_dirs}" CACHE INTERNAL "" FORCE)
|
||||
endif()
|
||||
endif()
|
||||
if(TARGET jsoncpp_lib_static AND NOT JSONCPP_IMPORTED_INCLUDE_DIRS)
|
||||
get_property(__jsoncpp_interface_include_dirs TARGET jsoncpp_lib_static PROPERTY INTERFACE_INCLUDE_DIRECTORIES)
|
||||
if(__jsoncpp_interface_include_dirs)
|
||||
set(JSONCPP_IMPORTED_INCLUDE_DIRS "${__jsoncpp_interface_include_dirs}" CACHE INTERNAL "" FORCE)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# As a convenience...
|
||||
if(TARGET jsoncpp_lib_static AND NOT TARGET jsoncpp_lib)
|
||||
add_library(jsoncpp_lib INTERFACE)
|
||||
target_link_libraries(jsoncpp_lib INTERFACE jsoncpp_lib_static)
|
||||
endif()
|
||||
|
||||
if(JSONCPP_IMPORTED_LIBRARY)
|
||||
if(NOT JSONCPP_IMPORTED_INCLUDE_DIRS)
|
||||
# OK, so we couldn't get it from the target... maybe we can figure it out from jsoncpp_DIR.
|
||||
|
||||
# take off the jsoncpp component
|
||||
get_filename_component(__jsoncpp_import_root "${jsoncpp_DIR}/.." ABSOLUTE)
|
||||
set(__jsoncpp_hints "${__jsoncpp_import_root}")
|
||||
# take off the cmake component
|
||||
get_filename_component(__jsoncpp_import_root "${__jsoncpp_import_root}/.." ABSOLUTE)
|
||||
list(APPEND __jsoncpp_hints "${__jsoncpp_import_root}")
|
||||
# take off the lib component
|
||||
get_filename_component(__jsoncpp_import_root "${__jsoncpp_import_root}/.." ABSOLUTE)
|
||||
list(APPEND __jsoncpp_hints "${__jsoncpp_import_root}")
|
||||
# take off one more component in case of multiarch lib
|
||||
get_filename_component(__jsoncpp_import_root "${__jsoncpp_import_root}/.." ABSOLUTE)
|
||||
list(APPEND __jsoncpp_hints "${__jsoncpp_import_root}")
|
||||
|
||||
# Now, search.
|
||||
find_path(JsonCpp_INCLUDE_DIR
|
||||
NAMES
|
||||
json/json.h
|
||||
PATH_SUFFIXES include jsoncpp include/jsoncpp
|
||||
HINTS ${__jsoncpp_hints})
|
||||
if(JsonCpp_INCLUDE_DIR)
|
||||
mark_as_advanced(JsonCpp_INCLUDE_DIR)
|
||||
# Note - this does not set it in the cache, in case we find it better at some point in the future!
|
||||
set(JSONCPP_IMPORTED_INCLUDE_DIRS ${JsonCpp_INCLUDE_DIR})
|
||||
endif()
|
||||
endif()
|
||||
|
||||
find_package_handle_standard_args(JsonCpp
|
||||
DEFAULT_MSG
|
||||
jsoncpp_DIR
|
||||
JSONCPP_IMPORTED_LIBRARY
|
||||
JSONCPP_IMPORTED_INCLUDE_DIRS)
|
||||
endif()
|
||||
|
||||
if(JSONCPP_FOUND)
|
||||
# Create any missing namespaced targets from the config module.
|
||||
if(__jsoncpp_have_namespaced_targets)
|
||||
if(JSONCPP_IMPORTED_LIBRARY AND NOT TARGET JsonCpp::JsonCpp)
|
||||
add_library(JsonCpp::JsonCpp INTERFACE IMPORTED)
|
||||
set_target_properties(JsonCpp::JsonCpp PROPERTIES
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${JSONCPP_IMPORTED_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${JSONCPP_IMPORTED_LIBRARY}")
|
||||
endif()
|
||||
|
||||
if(JSONCPP_IMPORTED_LIBRARY_SHARED AND NOT TARGET JsonCpp::JsonCppShared)
|
||||
add_library(JsonCpp::JsonCppShared INTERFACE IMPORTED)
|
||||
set_target_properties(JsonCpp::JsonCppShared PROPERTIES
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${JSONCPP_IMPORTED_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${JSONCPP_IMPORTED_LIBRARY_SHARED}")
|
||||
endif()
|
||||
|
||||
if(JSONCPP_IMPORTED_LIBRARY_STATIC AND NOT TARGET JsonCpp::JsonCppStatic)
|
||||
add_library(JsonCpp::JsonCppStatic INTERFACE IMPORTED)
|
||||
set_target_properties(JsonCpp::JsonCppStatic PROPERTIES
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${JSONCPP_IMPORTED_INCLUDE_DIRS}"
|
||||
INTERFACE_LINK_LIBRARIES "${JSONCPP_IMPORTED_LIBRARY_STATIC}")
|
||||
endif()
|
||||
|
||||
# Hide the stuff we didn't, and no longer, need.
|
||||
if(NOT JsonCpp_LIBRARY)
|
||||
unset(JsonCpp_LIBRARY CACHE)
|
||||
endif()
|
||||
if(NOT JsonCpp_INCLUDE_DIR)
|
||||
unset(JsonCpp_INCLUDE_DIR CACHE)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
set(JSONCPP_LIBRARY ${JSONCPP_IMPORTED_LIBRARY})
|
||||
set(JSONCPP_INCLUDE_DIRS ${JSONCPP_IMPORTED_INCLUDE_DIRS})
|
||||
if(DEFINED JSONCPP_IMPORTED_LIBRARY_IS_SHARED)
|
||||
set(JSONCPP_LIBRARY_IS_SHARED ${JSONCPP_IMPORTED_LIBRARY_IS_SHARED})
|
||||
else()
|
||||
unset(JSONCPP_LIBRARY_IS_SHARED)
|
||||
endif()
|
||||
|
||||
if(JSONCPP_IMPORTED_LIBRARY_SHARED)
|
||||
set(JSONCPP_LIBRARY_SHARED ${JSONCPP_IMPORTED_LIBRARY_SHARED})
|
||||
endif()
|
||||
|
||||
if(JSONCPP_IMPORTED_LIBRARY_STATIC)
|
||||
set(JSONCPP_LIBRARY_STATIC ${JSONCPP_IMPORTED_LIBRARY_STATIC})
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# Still nothing after looking for the config file: must go "old-school"
|
||||
if(NOT JSONCPP_FOUND)
|
||||
# Invoke pkgconfig for hints
|
||||
find_package(PkgConfig QUIET)
|
||||
set(_JSONCPP_INCLUDE_HINTS)
|
||||
set(_JSONCPP_LIB_HINTS)
|
||||
if(PKG_CONFIG_FOUND)
|
||||
pkg_search_module(_JSONCPP_PC QUIET jsoncpp)
|
||||
if(_JSONCPP_PC_INCLUDE_DIRS)
|
||||
set(_JSONCPP_INCLUDE_HINTS ${_JSONCPP_PC_INCLUDE_DIRS})
|
||||
endif()
|
||||
if(_JSONCPP_PC_LIBRARY_DIRS)
|
||||
set(_JSONCPP_LIB_HINTS ${_JSONCPP_PC_LIBRARY_DIRS})
|
||||
endif()
|
||||
if(_JSONCPP_PC_LIBRARIES)
|
||||
set(_JSONCPP_LIB_NAMES ${_JSONCPP_PC_LIBRARIES})
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT _JSONCPP_LIB_NAMES)
|
||||
# OK, if pkg-config wasn't able to give us a library name suggestion, then we may
|
||||
# have to resort to some intense old logic.
|
||||
set(_JSONCPP_LIB_NAMES jsoncpp)
|
||||
set(_JSONCPP_PATHSUFFIXES)
|
||||
|
||||
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES
|
||||
linux-gcc) # bit of a generalization but close...
|
||||
endif()
|
||||
if(CMAKE_COMPILER_IS_GNUCXX AND CMAKE_SYSTEM_NAME STREQUAL "Linux")
|
||||
list(APPEND
|
||||
_JSONCPP_LIB_NAMES
|
||||
json_linux-gcc-${CMAKE_CXX_COMPILER_VERSION}_libmt
|
||||
json_linux-gcc_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES
|
||||
linux-gcc-${CMAKE_CXX_COMPILER_VERSION})
|
||||
|
||||
elseif(MSVC)
|
||||
if(MSVC_VERSION EQUAL 1200)
|
||||
list(APPEND _JSONCPP_LIB_NAMES json_vc6_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES msvc6)
|
||||
elseif(MSVC_VERSION EQUAL 1300)
|
||||
list(APPEND _JSONCPP_LIB_NAMES json_vc7_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES msvc7)
|
||||
elseif(MSVC_VERSION EQUAL 1310)
|
||||
list(APPEND _JSONCPP_LIB_NAMES json_vc71_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES msvc71)
|
||||
elseif(MSVC_VERSION EQUAL 1400)
|
||||
list(APPEND _JSONCPP_LIB_NAMES json_vc8_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES msvc80)
|
||||
elseif(MSVC_VERSION EQUAL 1500)
|
||||
list(APPEND _JSONCPP_LIB_NAMES json_vc9_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES msvc90)
|
||||
elseif(MSVC_VERSION EQUAL 1600)
|
||||
list(APPEND _JSONCPP_LIB_NAMES json_vc10_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES msvc10 msvc100)
|
||||
endif()
|
||||
|
||||
elseif(MINGW)
|
||||
list(APPEND _JSONCPP_LIB_NAMES
|
||||
json_mingw_libmt)
|
||||
list(APPEND _JSONCPP_PATHSUFFIXES mingw)
|
||||
|
||||
else()
|
||||
list(APPEND _JSONCPP_LIB_NAMES
|
||||
json_suncc_libmt
|
||||
json_vacpp_libmt)
|
||||
endif()
|
||||
endif() # end of old logic
|
||||
|
||||
# Actually go looking.
|
||||
find_path(JsonCpp_INCLUDE_DIR
|
||||
NAMES
|
||||
json/json.h
|
||||
PATH_SUFFIXES jsoncpp
|
||||
HINTS ${_JSONCPP_INCLUDE_HINTS})
|
||||
find_library(JsonCpp_LIBRARY
|
||||
NAMES
|
||||
${_JSONCPP_LIB_NAMES}
|
||||
PATHS libs
|
||||
PATH_SUFFIXES ${_JSONCPP_PATHSUFFIXES}
|
||||
HINTS ${_JSONCPP_LIB_HINTS})
|
||||
|
||||
find_package_handle_standard_args(JsonCpp
|
||||
DEFAULT_MSG
|
||||
JsonCpp_INCLUDE_DIR
|
||||
JsonCpp_LIBRARY)
|
||||
|
||||
if(JSONCPP_FOUND)
|
||||
# We already know that the target doesn't exist, let's make it.
|
||||
# TODO don't know why we get errors like:
|
||||
# error: 'JsonCpp::JsonCpp-NOTFOUND', needed by 'bin/osvr_json_to_c', missing and no known rule to make it
|
||||
# when we do the imported target commented out below. So, instead, we make an interface
|
||||
# target with an alias. Hmm.
|
||||
|
||||
#add_library(JsonCpp::JsonCpp UNKNOWN IMPORTED)
|
||||
#set_target_properties(JsonCpp::JsonCpp PROPERTIES
|
||||
# IMPORTED_LOCATION "${JsonCpp_LIBRARY}"
|
||||
# INTERFACE_INCLUDE_DIRECTORIES "${JsonCpp_INCLUDE_DIR}"
|
||||
# IMPORTED_LINK_INTERFACE_LANGUAGES "CXX")
|
||||
|
||||
set(JSONCPP_LIBRARY "${JsonCpp_LIBRARY}")
|
||||
set(JSONCPP_INCLUDE_DIRS "${JsonCpp_INCLUDE_DIR}")
|
||||
unset(JSONCPP_LIBRARY_IS_SHARED)
|
||||
|
||||
if(__jsoncpp_have_interface_support AND NOT TARGET jsoncpp_interface)
|
||||
add_library(jsoncpp_interface INTERFACE)
|
||||
set_target_properties(jsoncpp_interface PROPERTIES
|
||||
INTERFACE_LINK_LIBRARIES "${JsonCpp_LIBRARY}"
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${JsonCpp_INCLUDE_DIR}")
|
||||
endif()
|
||||
if(__jsoncpp_have_namespaced_targets)
|
||||
if(NOT TARGET JsonCpp::JsonCpp)
|
||||
add_library(JsonCpp::JsonCpp ALIAS jsoncpp_interface)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(JSONCPP_FOUND)
|
||||
mark_as_advanced(jsoncpp_DIR JsonCpp_INCLUDE_DIR JsonCpp_LIBRARY)
|
||||
endif()
|
|
@ -1,86 +0,0 @@
|
|||
# - Try to find the OggVorbis libraries
|
||||
# Once done this will define
|
||||
#
|
||||
# OGGVORBIS_FOUND - system has OggVorbis
|
||||
# OGGVORBIS_VERSION - set either to 1 or 2
|
||||
# OGG_INCLUDE_DIR - the OggVorbis include directory
|
||||
# VORBIS_INCLUDE_DIR - the OggVorbis include directory
|
||||
# OGGVORBIS_LIBRARIES - The libraries needed to use OggVorbis
|
||||
# OGG_LIBRARY - The Ogg library
|
||||
# VORBIS_LIBRARY - The Vorbis library
|
||||
# VORBISFILE_LIBRARY - The VorbisFile library
|
||||
# VORBISENC_LIBRARY - The VorbisEnc library
|
||||
|
||||
# Copyright (c) 2006, Richard Laerkaeng, <richard@goteborg.utfors.se>
|
||||
#
|
||||
# Redistribution and use is allowed according to the terms of the BSD license.
|
||||
# For details see the accompanying COPYING-CMAKE-SCRIPTS file.
|
||||
|
||||
|
||||
include (CheckLibraryExists)
|
||||
|
||||
find_path(VORBIS_INCLUDE_DIR vorbis/vorbisfile.h)
|
||||
find_path(OGG_INCLUDE_DIR ogg/ogg.h)
|
||||
|
||||
find_library(OGG_LIBRARY NAMES ogg)
|
||||
find_library(VORBIS_LIBRARY NAMES vorbis)
|
||||
find_library(VORBISFILE_LIBRARY NAMES vorbisfile)
|
||||
find_library(VORBISENC_LIBRARY NAMES vorbisenc)
|
||||
|
||||
|
||||
if (VORBIS_INCLUDE_DIR AND VORBIS_LIBRARY AND VORBISFILE_LIBRARY AND VORBISENC_LIBRARY)
|
||||
set(OGGVORBIS_FOUND TRUE)
|
||||
|
||||
set(OGGVORBIS_LIBRARIES ${OGG_LIBRARY} ${VORBIS_LIBRARY} ${VORBISFILE_LIBRARY} ${VORBISENC_LIBRARY})
|
||||
|
||||
set(_CMAKE_REQUIRED_LIBRARIES_TMP ${CMAKE_REQUIRED_LIBRARIES})
|
||||
set(CMAKE_REQUIRED_LIBRARIES ${CMAKE_REQUIRED_LIBRARIES} ${OGGVORBIS_LIBRARIES})
|
||||
check_library_exists(vorbis vorbis_bitrate_addblock "" HAVE_LIBVORBISENC2)
|
||||
set(CMAKE_REQUIRED_LIBRARIES ${_CMAKE_REQUIRED_LIBRARIES_TMP})
|
||||
|
||||
if (HAVE_LIBVORBISENC2)
|
||||
set (OGGVORBIS_VERSION 2)
|
||||
else (HAVE_LIBVORBISENC2)
|
||||
set (OGGVORBIS_VERSION 1)
|
||||
endif (HAVE_LIBVORBISENC2)
|
||||
|
||||
else (VORBIS_INCLUDE_DIR AND VORBIS_LIBRARY AND VORBISFILE_LIBRARY AND VORBISENC_LIBRARY)
|
||||
set (OGGVORBIS_VERSION)
|
||||
set(OGGVORBIS_FOUND FALSE)
|
||||
endif (VORBIS_INCLUDE_DIR AND VORBIS_LIBRARY AND VORBISFILE_LIBRARY AND VORBISENC_LIBRARY)
|
||||
|
||||
|
||||
if (OGGVORBIS_FOUND)
|
||||
if (NOT OggVorbis_FIND_QUIETLY)
|
||||
message(STATUS "Found OggVorbis: ${OGGVORBIS_LIBRARIES}")
|
||||
endif (NOT OggVorbis_FIND_QUIETLY)
|
||||
else (OGGVORBIS_FOUND)
|
||||
if (OggVorbis_FIND_REQUIRED)
|
||||
message(FATAL_ERROR "Could NOT find OggVorbis libraries")
|
||||
endif (OggVorbis_FIND_REQUIRED)
|
||||
if (NOT OggVorbis_FIND_QUITELY)
|
||||
message(STATUS "Could NOT find OggVorbis libraries")
|
||||
endif (NOT OggVorbis_FIND_QUITELY)
|
||||
endif (OGGVORBIS_FOUND)
|
||||
|
||||
#check_include_files(vorbis/vorbisfile.h HAVE_VORBISFILE_H)
|
||||
#check_library_exists(ogg ogg_page_version "" HAVE_LIBOGG)
|
||||
#check_library_exists(vorbis vorbis_info_init "" HAVE_LIBVORBIS)
|
||||
#check_library_exists(vorbisfile ov_open "" HAVE_LIBVORBISFILE)
|
||||
#check_library_exists(vorbisenc vorbis_info_clear "" HAVE_LIBVORBISENC)
|
||||
#check_library_exists(vorbis vorbis_bitrate_addblock "" HAVE_LIBVORBISENC2)
|
||||
|
||||
#if (HAVE_LIBOGG AND HAVE_VORBISFILE_H AND HAVE_LIBVORBIS AND HAVE_LIBVORBISFILE AND HAVE_LIBVORBISENC)
|
||||
# message(STATUS "Ogg/Vorbis found")
|
||||
# set (VORBIS_LIBS "-lvorbis -logg")
|
||||
# set (VORBISFILE_LIBS "-lvorbisfile")
|
||||
# set (VORBISENC_LIBS "-lvorbisenc")
|
||||
# set (OGGVORBIS_FOUND TRUE)
|
||||
# if (HAVE_LIBVORBISENC2)
|
||||
# set (HAVE_VORBIS 2)
|
||||
# else (HAVE_LIBVORBISENC2)
|
||||
# set (HAVE_VORBIS 1)
|
||||
# endif (HAVE_LIBVORBISENC2)
|
||||
#else (HAVE_LIBOGG AND HAVE_VORBISFILE_H AND HAVE_LIBVORBIS AND HAVE_LIBVORBISFILE AND HAVE_LIBVORBISENC)
|
||||
# message(STATUS "Ogg/Vorbis not found")
|
||||
#endif (HAVE_LIBOGG AND HAVE_VORBISFILE_H AND HAVE_LIBVORBIS AND HAVE_LIBVORBISFILE AND HAVE_LIBVORBISENC)
|
|
@ -1,61 +0,0 @@
|
|||
# - Try to find png++
|
||||
#
|
||||
# The following variables are optionally searched for defaults
|
||||
# png++_ROOT_DIR: Base directory where all GLOG components are found
|
||||
#
|
||||
# The following are set after configuration is done:
|
||||
# png++_FOUND
|
||||
# png++_INCLUDE_DIRS
|
||||
# png++_LIBRARIES
|
||||
|
||||
find_package(PNG REQUIRED)
|
||||
|
||||
include(FindPackageHandleStandardArgs)
|
||||
|
||||
set(png++_ROOT_DIR "" CACHE PATH "Folder contains png++")
|
||||
|
||||
find_path(png++_INCLUDE_DIR
|
||||
NAMES
|
||||
png++/color.hpp
|
||||
png++/config.hpp
|
||||
png++/consumer.hpp
|
||||
png++/convert_color_space.hpp
|
||||
png++/end_info.hpp
|
||||
png++/error.hpp
|
||||
png++/ga_pixel.hpp
|
||||
png++/generator.hpp
|
||||
png++/gray_pixel.hpp
|
||||
png++/image.hpp
|
||||
png++/image_info.hpp
|
||||
png++/index_pixel.hpp
|
||||
png++/info.hpp
|
||||
png++/info_base.hpp
|
||||
png++/io_base.hpp
|
||||
png++/packed_pixel.hpp
|
||||
png++/palette.hpp
|
||||
png++/pixel_buffer.hpp
|
||||
png++/pixel_traits.hpp
|
||||
png++/png.hpp
|
||||
png++/reader.hpp
|
||||
png++/require_color_space.hpp
|
||||
png++/rgb_pixel.hpp
|
||||
png++/rgba_pixel.hpp
|
||||
png++/streaming_base.hpp
|
||||
png++/tRNS.hpp
|
||||
png++/types.hpp
|
||||
png++/writer.hpp
|
||||
PATHS
|
||||
${png++_ROOT_DIR}
|
||||
PATH_SUFFIXES
|
||||
src)
|
||||
|
||||
set(png++_INCLUDE_DIRS ${png++_INCLUDE_DIR} ${PNG_INCLUDE_DIRS})
|
||||
set(png++_LIBRARIES ${PNG_LIBRARIES})
|
||||
|
||||
find_package_handle_standard_args(png++ DEFAULT_MSG
|
||||
png++_INCLUDE_DIR)
|
||||
|
||||
if(png++_FOUND)
|
||||
set(png++_INCLUDE_DIRS ${png++_INCLUDE_DIR})
|
||||
set(png++_LIBRARIES ${png++_LIBRARY})
|
||||
endif()
|
|
@ -0,0 +1,525 @@
|
|||
# Copyright 2010-2011,2014 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
if(DEFINED __INCLUDED_GR_MISC_UTILS_CMAKE)
|
||||
return()
|
||||
endif()
|
||||
set(__INCLUDED_GR_MISC_UTILS_CMAKE TRUE)
|
||||
|
||||
########################################################################
|
||||
# Set global variable macro.
|
||||
# Used for subdirectories to export settings.
|
||||
# Example: include and library paths.
|
||||
########################################################################
|
||||
function(GR_SET_GLOBAL var)
|
||||
set(${var} ${ARGN} CACHE INTERNAL "" FORCE)
|
||||
endfunction(GR_SET_GLOBAL)
|
||||
|
||||
########################################################################
|
||||
# Set the pre-processor definition if the condition is true.
|
||||
# - def the pre-processor definition to set and condition name
|
||||
########################################################################
|
||||
function(GR_ADD_COND_DEF def)
|
||||
if(${def})
|
||||
add_definitions(-D${def})
|
||||
endif(${def})
|
||||
endfunction(GR_ADD_COND_DEF)
|
||||
|
||||
########################################################################
|
||||
# Check for a header and conditionally set a compile define.
|
||||
# - hdr the relative path to the header file
|
||||
# - def the pre-processor definition to set
|
||||
########################################################################
|
||||
function(GR_CHECK_HDR_N_DEF hdr def)
|
||||
include(CheckIncludeFileCXX)
|
||||
CHECK_INCLUDE_FILE_CXX(${hdr} ${def})
|
||||
GR_ADD_COND_DEF(${def})
|
||||
endfunction(GR_CHECK_HDR_N_DEF)
|
||||
|
||||
########################################################################
|
||||
# Include subdirectory macro.
|
||||
# Sets the CMake directory variables,
|
||||
# includes the subdirectory CMakeLists.txt,
|
||||
# resets the CMake directory variables.
|
||||
#
|
||||
# This macro includes subdirectories rather than adding them
|
||||
# so that the subdirectory can affect variables in the level above.
|
||||
# This provides a work-around for the lack of convenience libraries.
|
||||
# This way a subdirectory can append to the list of library sources.
|
||||
########################################################################
|
||||
macro(GR_INCLUDE_SUBDIRECTORY subdir)
|
||||
#insert the current directories on the front of the list
|
||||
list(INSERT _cmake_source_dirs 0 ${CMAKE_CURRENT_SOURCE_DIR})
|
||||
list(INSERT _cmake_binary_dirs 0 ${CMAKE_CURRENT_BINARY_DIR})
|
||||
|
||||
#set the current directories to the names of the subdirs
|
||||
set(CMAKE_CURRENT_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/${subdir})
|
||||
set(CMAKE_CURRENT_BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/${subdir})
|
||||
|
||||
#include the subdirectory CMakeLists to run it
|
||||
file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
|
||||
include(${CMAKE_CURRENT_SOURCE_DIR}/CMakeLists.txt)
|
||||
|
||||
#reset the value of the current directories
|
||||
list(GET _cmake_source_dirs 0 CMAKE_CURRENT_SOURCE_DIR)
|
||||
list(GET _cmake_binary_dirs 0 CMAKE_CURRENT_BINARY_DIR)
|
||||
|
||||
#pop the subdir names of the front of the list
|
||||
list(REMOVE_AT _cmake_source_dirs 0)
|
||||
list(REMOVE_AT _cmake_binary_dirs 0)
|
||||
endmacro(GR_INCLUDE_SUBDIRECTORY)
|
||||
|
||||
########################################################################
|
||||
# Check if a compiler flag works and conditionally set a compile define.
|
||||
# - flag the compiler flag to check for
|
||||
# - have the variable to set with result
|
||||
########################################################################
|
||||
macro(GR_ADD_CXX_COMPILER_FLAG_IF_AVAILABLE flag have)
|
||||
include(CheckCXXCompilerFlag)
|
||||
CHECK_CXX_COMPILER_FLAG(${flag} ${have})
|
||||
if(${have})
|
||||
if(${CMAKE_VERSION} VERSION_GREATER "2.8.4")
|
||||
STRING(FIND "${CMAKE_CXX_FLAGS}" "${flag}" flag_dup)
|
||||
if(${flag_dup} EQUAL -1)
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${flag}")
|
||||
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${flag}")
|
||||
endif(${flag_dup} EQUAL -1)
|
||||
endif(${CMAKE_VERSION} VERSION_GREATER "2.8.4")
|
||||
endif(${have})
|
||||
endmacro(GR_ADD_CXX_COMPILER_FLAG_IF_AVAILABLE)
|
||||
|
||||
########################################################################
|
||||
# Generates the .la libtool file
|
||||
# This appears to generate libtool files that cannot be used by auto*.
|
||||
# Usage GR_LIBTOOL(TARGET [target] DESTINATION [dest])
|
||||
# Notice: there is not COMPONENT option, these will not get distributed.
|
||||
########################################################################
|
||||
function(GR_LIBTOOL)
|
||||
if(NOT DEFINED GENERATE_LIBTOOL)
|
||||
set(GENERATE_LIBTOOL OFF) #disabled by default
|
||||
endif()
|
||||
|
||||
if(GENERATE_LIBTOOL)
|
||||
include(CMakeParseArgumentsCopy)
|
||||
CMAKE_PARSE_ARGUMENTS(GR_LIBTOOL "" "TARGET;DESTINATION" "" ${ARGN})
|
||||
|
||||
find_program(LIBTOOL libtool)
|
||||
if(LIBTOOL)
|
||||
include(CMakeMacroLibtoolFile)
|
||||
CREATE_LIBTOOL_FILE(${GR_LIBTOOL_TARGET} /${GR_LIBTOOL_DESTINATION})
|
||||
endif(LIBTOOL)
|
||||
endif(GENERATE_LIBTOOL)
|
||||
|
||||
endfunction(GR_LIBTOOL)
|
||||
|
||||
########################################################################
|
||||
# Do standard things to the library target
|
||||
# - set target properties
|
||||
# - make install rules
|
||||
# Also handle gnuradio custom naming conventions w/ extras mode.
|
||||
########################################################################
|
||||
function(GR_LIBRARY_FOO target)
|
||||
#parse the arguments for component names
|
||||
include(CMakeParseArgumentsCopy)
|
||||
CMAKE_PARSE_ARGUMENTS(GR_LIBRARY "" "RUNTIME_COMPONENT;DEVEL_COMPONENT" "" ${ARGN})
|
||||
|
||||
#set additional target properties
|
||||
set_target_properties(${target} PROPERTIES SOVERSION ${LIBVER})
|
||||
|
||||
#install the generated files like so...
|
||||
install(TARGETS ${target}
|
||||
LIBRARY DESTINATION ${GR_LIBRARY_DIR} COMPONENT ${GR_LIBRARY_RUNTIME_COMPONENT} # .so/.dylib file
|
||||
ARCHIVE DESTINATION ${GR_LIBRARY_DIR} COMPONENT ${GR_LIBRARY_DEVEL_COMPONENT} # .lib file
|
||||
RUNTIME DESTINATION ${GR_RUNTIME_DIR} COMPONENT ${GR_LIBRARY_RUNTIME_COMPONENT} # .dll file
|
||||
)
|
||||
|
||||
#extras mode enabled automatically on linux
|
||||
if(NOT DEFINED LIBRARY_EXTRAS)
|
||||
set(LIBRARY_EXTRAS ${LINUX})
|
||||
endif()
|
||||
|
||||
#special extras mode to enable alternative naming conventions
|
||||
if(LIBRARY_EXTRAS)
|
||||
|
||||
#create .la file before changing props
|
||||
GR_LIBTOOL(TARGET ${target} DESTINATION ${GR_LIBRARY_DIR})
|
||||
|
||||
#give the library a special name with ultra-zero soversion
|
||||
set_target_properties(${target} PROPERTIES OUTPUT_NAME ${target}-${LIBVER} SOVERSION "0.0.0")
|
||||
set(target_name lib${target}-${LIBVER}.so.0.0.0)
|
||||
|
||||
#custom command to generate symlinks
|
||||
add_custom_command(
|
||||
TARGET ${target}
|
||||
POST_BUILD
|
||||
COMMAND ${CMAKE_COMMAND} -E create_symlink ${target_name} ${CMAKE_CURRENT_BINARY_DIR}/lib${target}.so
|
||||
COMMAND ${CMAKE_COMMAND} -E create_symlink ${target_name} ${CMAKE_CURRENT_BINARY_DIR}/lib${target}-${LIBVER}.so.0
|
||||
COMMAND ${CMAKE_COMMAND} -E touch ${target_name} #so the symlinks point to something valid so cmake 2.6 will install
|
||||
)
|
||||
|
||||
#and install the extra symlinks
|
||||
install(
|
||||
FILES
|
||||
${CMAKE_CURRENT_BINARY_DIR}/lib${target}.so
|
||||
${CMAKE_CURRENT_BINARY_DIR}/lib${target}-${LIBVER}.so.0
|
||||
DESTINATION ${GR_LIBRARY_DIR} COMPONENT ${GR_LIBRARY_RUNTIME_COMPONENT}
|
||||
)
|
||||
|
||||
endif(LIBRARY_EXTRAS)
|
||||
endfunction(GR_LIBRARY_FOO)
|
||||
|
||||
########################################################################
|
||||
# Create a dummy custom command that depends on other targets.
|
||||
# Usage:
|
||||
# GR_GEN_TARGET_DEPS(unique_name target_deps <target1> <target2> ...)
|
||||
# ADD_CUSTOM_COMMAND(<the usual args> ${target_deps})
|
||||
#
|
||||
# Custom command cant depend on targets, but can depend on executables,
|
||||
# and executables can depend on targets. So this is the process:
|
||||
########################################################################
|
||||
function(GR_GEN_TARGET_DEPS name var)
|
||||
file(
|
||||
WRITE ${CMAKE_CURRENT_BINARY_DIR}/${name}.cpp.in
|
||||
"int main(void){return 0;}\n"
|
||||
)
|
||||
execute_process(
|
||||
COMMAND ${CMAKE_COMMAND} -E copy_if_different
|
||||
${CMAKE_CURRENT_BINARY_DIR}/${name}.cpp.in
|
||||
${CMAKE_CURRENT_BINARY_DIR}/${name}.cpp
|
||||
)
|
||||
add_executable(${name} ${CMAKE_CURRENT_BINARY_DIR}/${name}.cpp)
|
||||
if(ARGN)
|
||||
add_dependencies(${name} ${ARGN})
|
||||
endif(ARGN)
|
||||
|
||||
if(CMAKE_CROSSCOMPILING)
|
||||
set(${var} "DEPENDS;${name}" PARENT_SCOPE) #cant call command when cross
|
||||
else()
|
||||
set(${var} "DEPENDS;${name};COMMAND;${name}" PARENT_SCOPE)
|
||||
endif()
|
||||
endfunction(GR_GEN_TARGET_DEPS)
|
||||
|
||||
########################################################################
|
||||
# Control use of gr_logger
|
||||
# Usage:
|
||||
# GR_LOGGING()
|
||||
#
|
||||
# Will set ENABLE_GR_LOG to 1 by default.
|
||||
# Can manually set with -DENABLE_GR_LOG=0|1
|
||||
########################################################################
|
||||
function(GR_LOGGING)
|
||||
find_package(Log4cpp)
|
||||
|
||||
OPTION(ENABLE_GR_LOG "Use gr_logger" ON)
|
||||
if(ENABLE_GR_LOG)
|
||||
# If gr_logger is enabled, make it usable
|
||||
add_definitions( -DENABLE_GR_LOG )
|
||||
|
||||
# also test LOG4CPP; if we have it, use this version of the logger
|
||||
# otherwise, default to the stdout/stderr model.
|
||||
if(LOG4CPP_FOUND)
|
||||
SET(HAVE_LOG4CPP True CACHE INTERNAL "" FORCE)
|
||||
add_definitions( -DHAVE_LOG4CPP )
|
||||
else(not LOG4CPP_FOUND)
|
||||
SET(HAVE_LOG4CPP False CACHE INTERNAL "" FORCE)
|
||||
SET(LOG4CPP_INCLUDE_DIRS "" CACHE INTERNAL "" FORCE)
|
||||
SET(LOG4CPP_LIBRARY_DIRS "" CACHE INTERNAL "" FORCE)
|
||||
SET(LOG4CPP_LIBRARIES "" CACHE INTERNAL "" FORCE)
|
||||
endif(LOG4CPP_FOUND)
|
||||
|
||||
SET(ENABLE_GR_LOG ${ENABLE_GR_LOG} CACHE INTERNAL "" FORCE)
|
||||
|
||||
else(ENABLE_GR_LOG)
|
||||
SET(HAVE_LOG4CPP False CACHE INTERNAL "" FORCE)
|
||||
SET(LOG4CPP_INCLUDE_DIRS "" CACHE INTERNAL "" FORCE)
|
||||
SET(LOG4CPP_LIBRARY_DIRS "" CACHE INTERNAL "" FORCE)
|
||||
SET(LOG4CPP_LIBRARIES "" CACHE INTERNAL "" FORCE)
|
||||
endif(ENABLE_GR_LOG)
|
||||
|
||||
message(STATUS "ENABLE_GR_LOG set to ${ENABLE_GR_LOG}.")
|
||||
message(STATUS "HAVE_LOG4CPP set to ${HAVE_LOG4CPP}.")
|
||||
message(STATUS "LOG4CPP_LIBRARIES set to ${LOG4CPP_LIBRARIES}.")
|
||||
|
||||
endfunction(GR_LOGGING)
|
||||
|
||||
########################################################################
|
||||
# Run GRCC to compile .grc files into .py files.
|
||||
#
|
||||
# Usage: GRCC(filename, directory)
|
||||
# - filenames: List of file name of .grc file
|
||||
# - directory: directory of built .py file - usually in
|
||||
# ${CMAKE_CURRENT_BINARY_DIR}
|
||||
# - Sets PYFILES: output converted GRC file names to Python files.
|
||||
########################################################################
|
||||
function(GRCC)
|
||||
# Extract directory from list of args, remove it for the list of filenames.
|
||||
list(GET ARGV -1 directory)
|
||||
list(REMOVE_AT ARGV -1)
|
||||
set(filenames ${ARGV})
|
||||
file(MAKE_DIRECTORY ${directory})
|
||||
|
||||
SET(GRCC_COMMAND ${CMAKE_SOURCE_DIR}/gr-utils/python/grcc)
|
||||
|
||||
# GRCC uses some stuff in grc and gnuradio-runtime, so we force
|
||||
# the known paths here
|
||||
list(APPEND PYTHONPATHS
|
||||
${CMAKE_SOURCE_DIR}
|
||||
${CMAKE_SOURCE_DIR}/gnuradio-runtime/python
|
||||
${CMAKE_SOURCE_DIR}/gnuradio-runtime/lib/swig
|
||||
${CMAKE_BINARY_DIR}/gnuradio-runtime/lib/swig
|
||||
)
|
||||
|
||||
if(WIN32)
|
||||
#SWIG generates the python library files into a subdirectory.
|
||||
#Therefore, we must append this subdirectory into PYTHONPATH.
|
||||
#Only do this for the python directories matching the following:
|
||||
foreach(pydir ${PYTHONPATHS})
|
||||
get_filename_component(name ${pydir} NAME)
|
||||
if(name MATCHES "^(swig|lib|src)$")
|
||||
list(APPEND PYTHONPATHS ${pydir}/${CMAKE_BUILD_TYPE})
|
||||
endif()
|
||||
endforeach(pydir)
|
||||
endif(WIN32)
|
||||
|
||||
file(TO_NATIVE_PATH "${PYTHONPATHS}" pypath)
|
||||
|
||||
if(UNIX)
|
||||
list(APPEND pypath "$PYTHONPATH")
|
||||
string(REPLACE ";" ":" pypath "${pypath}")
|
||||
set(ENV{PYTHONPATH} ${pypath})
|
||||
endif(UNIX)
|
||||
|
||||
if(WIN32)
|
||||
list(APPEND pypath "%PYTHONPATH%")
|
||||
string(REPLACE ";" "\\;" pypath "${pypath}")
|
||||
#list(APPEND environs "PYTHONPATH=${pypath}")
|
||||
set(ENV{PYTHONPATH} ${pypath})
|
||||
endif(WIN32)
|
||||
|
||||
foreach(f ${filenames})
|
||||
execute_process(
|
||||
COMMAND ${GRCC_COMMAND} -d ${directory} ${f}
|
||||
)
|
||||
string(REPLACE ".grc" ".py" pyfile "${f}")
|
||||
string(REPLACE "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_BINARY_DIR}" pyfile "${pyfile}")
|
||||
list(APPEND pyfiles ${pyfile})
|
||||
endforeach(f)
|
||||
|
||||
set(PYFILES ${pyfiles} PARENT_SCOPE)
|
||||
endfunction(GRCC)
|
||||
|
||||
########################################################################
|
||||
# Check if HAVE_PTHREAD_SETSCHEDPARAM and HAVE_SCHED_SETSCHEDULER
|
||||
# should be defined
|
||||
########################################################################
|
||||
macro(GR_CHECK_LINUX_SCHED_AVAIL)
|
||||
set(CMAKE_REQUIRED_LIBRARIES -lpthread)
|
||||
CHECK_CXX_SOURCE_COMPILES("
|
||||
#include <pthread.h>
|
||||
int main(){
|
||||
pthread_t pthread;
|
||||
pthread_setschedparam(pthread, 0, 0);
|
||||
return 0;
|
||||
} " HAVE_PTHREAD_SETSCHEDPARAM
|
||||
)
|
||||
GR_ADD_COND_DEF(HAVE_PTHREAD_SETSCHEDPARAM)
|
||||
|
||||
CHECK_CXX_SOURCE_COMPILES("
|
||||
#include <sched.h>
|
||||
int main(){
|
||||
pid_t pid;
|
||||
sched_setscheduler(pid, 0, 0);
|
||||
return 0;
|
||||
} " HAVE_SCHED_SETSCHEDULER
|
||||
)
|
||||
GR_ADD_COND_DEF(HAVE_SCHED_SETSCHEDULER)
|
||||
endmacro(GR_CHECK_LINUX_SCHED_AVAIL)
|
||||
|
||||
########################################################################
|
||||
# Macros to generate source and header files from template
|
||||
########################################################################
|
||||
macro(GR_EXPAND_X_H component root)
|
||||
|
||||
include(GrPython)
|
||||
|
||||
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
"#!${PYTHON_EXECUTABLE}
|
||||
|
||||
import sys, os, re
|
||||
sys.path.append('${GR_RUNTIME_PYTHONPATH}')
|
||||
os.environ['srcdir'] = '${CMAKE_CURRENT_SOURCE_DIR}'
|
||||
os.chdir('${CMAKE_CURRENT_BINARY_DIR}')
|
||||
|
||||
if __name__ == '__main__':
|
||||
import build_utils
|
||||
root, inp = sys.argv[1:3]
|
||||
for sig in sys.argv[3:]:
|
||||
name = re.sub ('X+', sig, root)
|
||||
d = build_utils.standard_dict2(name, sig, '${component}')
|
||||
build_utils.expand_template(d, inp)
|
||||
")
|
||||
|
||||
#make a list of all the generated headers
|
||||
unset(expanded_files_h)
|
||||
foreach(sig ${ARGN})
|
||||
string(REGEX REPLACE "X+" ${sig} name ${root})
|
||||
list(APPEND expanded_files_h ${CMAKE_CURRENT_BINARY_DIR}/${name}.h)
|
||||
endforeach(sig)
|
||||
unset(name)
|
||||
|
||||
#create a command to generate the headers
|
||||
add_custom_command(
|
||||
OUTPUT ${expanded_files_h}
|
||||
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}.h.t
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
|
||||
${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
${root} ${root}.h.t ${ARGN}
|
||||
)
|
||||
|
||||
#install rules for the generated headers
|
||||
list(APPEND generated_includes ${expanded_files_h})
|
||||
|
||||
endmacro(GR_EXPAND_X_H)
|
||||
|
||||
macro(GR_EXPAND_X_CC_H component root)
|
||||
|
||||
include(GrPython)
|
||||
|
||||
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
"#!${PYTHON_EXECUTABLE}
|
||||
|
||||
import sys, os, re
|
||||
sys.path.append('${GR_RUNTIME_PYTHONPATH}')
|
||||
os.environ['srcdir'] = '${CMAKE_CURRENT_SOURCE_DIR}'
|
||||
os.chdir('${CMAKE_CURRENT_BINARY_DIR}')
|
||||
|
||||
if __name__ == '__main__':
|
||||
import build_utils
|
||||
root, inp = sys.argv[1:3]
|
||||
for sig in sys.argv[3:]:
|
||||
name = re.sub ('X+', sig, root)
|
||||
d = build_utils.standard_impl_dict2(name, sig, '${component}')
|
||||
build_utils.expand_template(d, inp)
|
||||
")
|
||||
|
||||
#make a list of all the generated files
|
||||
unset(expanded_files_cc)
|
||||
unset(expanded_files_h)
|
||||
foreach(sig ${ARGN})
|
||||
string(REGEX REPLACE "X+" ${sig} name ${root})
|
||||
list(APPEND expanded_files_cc ${CMAKE_CURRENT_BINARY_DIR}/${name}.cc)
|
||||
list(APPEND expanded_files_h ${CMAKE_CURRENT_BINARY_DIR}/${name}.h)
|
||||
endforeach(sig)
|
||||
unset(name)
|
||||
|
||||
#create a command to generate the source files
|
||||
add_custom_command(
|
||||
OUTPUT ${expanded_files_cc}
|
||||
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}.cc.t
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
|
||||
${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
${root} ${root}.cc.t ${ARGN}
|
||||
)
|
||||
|
||||
#create a command to generate the header files
|
||||
add_custom_command(
|
||||
OUTPUT ${expanded_files_h}
|
||||
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}.h.t
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
|
||||
${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
${root} ${root}.h.t ${ARGN}
|
||||
)
|
||||
|
||||
#make source files depends on headers to force generation
|
||||
set_source_files_properties(${expanded_files_cc}
|
||||
PROPERTIES OBJECT_DEPENDS "${expanded_files_h}"
|
||||
)
|
||||
|
||||
#install rules for the generated files
|
||||
list(APPEND generated_sources ${expanded_files_cc})
|
||||
list(APPEND generated_headers ${expanded_files_h})
|
||||
|
||||
endmacro(GR_EXPAND_X_CC_H)
|
||||
|
||||
macro(GR_EXPAND_X_CC_H_IMPL component root)
|
||||
|
||||
include(GrPython)
|
||||
|
||||
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
"#!${PYTHON_EXECUTABLE}
|
||||
|
||||
import sys, os, re
|
||||
sys.path.append('${GR_RUNTIME_PYTHONPATH}')
|
||||
os.environ['srcdir'] = '${CMAKE_CURRENT_SOURCE_DIR}'
|
||||
os.chdir('${CMAKE_CURRENT_BINARY_DIR}')
|
||||
|
||||
if __name__ == '__main__':
|
||||
import build_utils
|
||||
root, inp = sys.argv[1:3]
|
||||
for sig in sys.argv[3:]:
|
||||
name = re.sub ('X+', sig, root)
|
||||
d = build_utils.standard_dict(name, sig, '${component}')
|
||||
build_utils.expand_template(d, inp, '_impl')
|
||||
")
|
||||
|
||||
#make a list of all the generated files
|
||||
unset(expanded_files_cc_impl)
|
||||
unset(expanded_files_h_impl)
|
||||
unset(expanded_files_h)
|
||||
foreach(sig ${ARGN})
|
||||
string(REGEX REPLACE "X+" ${sig} name ${root})
|
||||
list(APPEND expanded_files_cc_impl ${CMAKE_CURRENT_BINARY_DIR}/${name}_impl.cc)
|
||||
list(APPEND expanded_files_h_impl ${CMAKE_CURRENT_BINARY_DIR}/${name}_impl.h)
|
||||
list(APPEND expanded_files_h ${CMAKE_CURRENT_BINARY_DIR}/../include/gnuradio/${component}/${name}.h)
|
||||
endforeach(sig)
|
||||
unset(name)
|
||||
|
||||
#create a command to generate the _impl.cc files
|
||||
add_custom_command(
|
||||
OUTPUT ${expanded_files_cc_impl}
|
||||
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}_impl.cc.t
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
|
||||
${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
${root} ${root}_impl.cc.t ${ARGN}
|
||||
)
|
||||
|
||||
#create a command to generate the _impl.h files
|
||||
add_custom_command(
|
||||
OUTPUT ${expanded_files_h_impl}
|
||||
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${root}_impl.h.t
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
|
||||
${CMAKE_CURRENT_BINARY_DIR}/generate_helper.py
|
||||
${root} ${root}_impl.h.t ${ARGN}
|
||||
)
|
||||
|
||||
#make _impl.cc source files depend on _impl.h to force generation
|
||||
set_source_files_properties(${expanded_files_cc_impl}
|
||||
PROPERTIES OBJECT_DEPENDS "${expanded_files_h_impl}"
|
||||
)
|
||||
|
||||
#make _impl.h source files depend on headers to force generation
|
||||
set_source_files_properties(${expanded_files_h_impl}
|
||||
PROPERTIES OBJECT_DEPENDS "${expanded_files_h}"
|
||||
)
|
||||
|
||||
#install rules for the generated files
|
||||
list(APPEND generated_sources ${expanded_files_cc_impl})
|
||||
list(APPEND generated_headers ${expanded_files_h_impl})
|
||||
|
||||
endmacro(GR_EXPAND_X_CC_H_IMPL)
|
|
@ -0,0 +1,54 @@
|
|||
# Copyright 2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
if(DEFINED __INCLUDED_GR_PLATFORM_CMAKE)
|
||||
return()
|
||||
endif()
|
||||
set(__INCLUDED_GR_PLATFORM_CMAKE TRUE)
|
||||
|
||||
########################################################################
|
||||
# Setup additional defines for OS types
|
||||
########################################################################
|
||||
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
|
||||
set(LINUX TRUE)
|
||||
endif()
|
||||
|
||||
if(LINUX AND EXISTS "/etc/debian_version")
|
||||
set(DEBIAN TRUE)
|
||||
endif()
|
||||
|
||||
if(LINUX AND EXISTS "/etc/redhat-release")
|
||||
set(REDHAT TRUE)
|
||||
endif()
|
||||
|
||||
if(LINUX AND EXISTS "/etc/slackware-version")
|
||||
set(SLACKWARE TRUE)
|
||||
endif()
|
||||
|
||||
########################################################################
|
||||
# when the library suffix should be 64 (applies to redhat linux family)
|
||||
########################################################################
|
||||
if (REDHAT OR SLACKWARE)
|
||||
set(LIB64_CONVENTION TRUE)
|
||||
endif()
|
||||
|
||||
if(NOT DEFINED LIB_SUFFIX AND LIB64_CONVENTION AND CMAKE_SYSTEM_PROCESSOR MATCHES "64$")
|
||||
set(LIB_SUFFIX 64)
|
||||
endif()
|
||||
set(LIB_SUFFIX ${LIB_SUFFIX} CACHE STRING "lib directory suffix")
|
|
@ -0,0 +1,241 @@
|
|||
# Copyright 2010-2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
if(DEFINED __INCLUDED_GR_PYTHON_CMAKE)
|
||||
return()
|
||||
endif()
|
||||
set(__INCLUDED_GR_PYTHON_CMAKE TRUE)
|
||||
|
||||
########################################################################
|
||||
# Setup the python interpreter:
|
||||
# This allows the user to specify a specific interpreter,
|
||||
# or finds the interpreter via the built-in cmake module.
|
||||
########################################################################
|
||||
#this allows the user to override PYTHON_EXECUTABLE
|
||||
if(PYTHON_EXECUTABLE)
|
||||
|
||||
set(PYTHONINTERP_FOUND TRUE)
|
||||
|
||||
#otherwise if not set, try to automatically find it
|
||||
else(PYTHON_EXECUTABLE)
|
||||
|
||||
#use the built-in find script
|
||||
find_package(PythonInterp 2)
|
||||
|
||||
#and if that fails use the find program routine
|
||||
if(NOT PYTHONINTERP_FOUND)
|
||||
find_program(PYTHON_EXECUTABLE NAMES python python2 python2.7 python2.6 python2.5)
|
||||
if(PYTHON_EXECUTABLE)
|
||||
set(PYTHONINTERP_FOUND TRUE)
|
||||
endif(PYTHON_EXECUTABLE)
|
||||
endif(NOT PYTHONINTERP_FOUND)
|
||||
|
||||
endif(PYTHON_EXECUTABLE)
|
||||
|
||||
if (CMAKE_CROSSCOMPILING)
|
||||
set(QA_PYTHON_EXECUTABLE "/usr/bin/python")
|
||||
else (CMAKE_CROSSCOMPILING)
|
||||
set(QA_PYTHON_EXECUTABLE ${PYTHON_EXECUTABLE})
|
||||
endif(CMAKE_CROSSCOMPILING)
|
||||
|
||||
#make the path to the executable appear in the cmake gui
|
||||
set(PYTHON_EXECUTABLE ${PYTHON_EXECUTABLE} CACHE FILEPATH "python interpreter")
|
||||
set(QA_PYTHON_EXECUTABLE ${QA_PYTHON_EXECUTABLE} CACHE FILEPATH "python interpreter for QA tests")
|
||||
|
||||
#make sure we can use -B with python (introduced in 2.6)
|
||||
if(PYTHON_EXECUTABLE)
|
||||
execute_process(
|
||||
COMMAND ${PYTHON_EXECUTABLE} -B -c ""
|
||||
OUTPUT_QUIET ERROR_QUIET
|
||||
RESULT_VARIABLE PYTHON_HAS_DASH_B_RESULT
|
||||
)
|
||||
if(PYTHON_HAS_DASH_B_RESULT EQUAL 0)
|
||||
set(PYTHON_DASH_B "-B")
|
||||
endif()
|
||||
endif(PYTHON_EXECUTABLE)
|
||||
|
||||
########################################################################
|
||||
# Check for the existence of a python module:
|
||||
# - desc a string description of the check
|
||||
# - mod the name of the module to import
|
||||
# - cmd an additional command to run
|
||||
# - have the result variable to set
|
||||
########################################################################
|
||||
macro(GR_PYTHON_CHECK_MODULE desc mod cmd have)
|
||||
message(STATUS "")
|
||||
message(STATUS "Python checking for ${desc}")
|
||||
execute_process(
|
||||
COMMAND ${PYTHON_EXECUTABLE} -c "
|
||||
#########################################
|
||||
try:
|
||||
import ${mod}
|
||||
assert ${cmd}
|
||||
except ImportError, AssertionError: exit(-1)
|
||||
except: pass
|
||||
#########################################"
|
||||
RESULT_VARIABLE ${have}
|
||||
)
|
||||
if(${have} EQUAL 0)
|
||||
message(STATUS "Python checking for ${desc} - found")
|
||||
set(${have} TRUE)
|
||||
else(${have} EQUAL 0)
|
||||
message(STATUS "Python checking for ${desc} - not found")
|
||||
set(${have} FALSE)
|
||||
endif(${have} EQUAL 0)
|
||||
endmacro(GR_PYTHON_CHECK_MODULE)
|
||||
|
||||
########################################################################
|
||||
# Sets the python installation directory GR_PYTHON_DIR
|
||||
########################################################################
|
||||
if(NOT DEFINED GR_PYTHON_DIR)
|
||||
execute_process(COMMAND ${PYTHON_EXECUTABLE} -c "
|
||||
from distutils import sysconfig
|
||||
print sysconfig.get_python_lib(plat_specific=True, prefix='')
|
||||
" OUTPUT_VARIABLE GR_PYTHON_DIR OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
)
|
||||
endif()
|
||||
file(TO_CMAKE_PATH ${GR_PYTHON_DIR} GR_PYTHON_DIR)
|
||||
|
||||
########################################################################
|
||||
# Create an always-built target with a unique name
|
||||
# Usage: GR_UNIQUE_TARGET(<description> <dependencies list>)
|
||||
########################################################################
|
||||
function(GR_UNIQUE_TARGET desc)
|
||||
file(RELATIVE_PATH reldir ${CMAKE_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR})
|
||||
execute_process(COMMAND ${PYTHON_EXECUTABLE} -c "import re, hashlib
|
||||
unique = hashlib.md5('${reldir}${ARGN}').hexdigest()[:5]
|
||||
print(re.sub('\\W', '_', '${desc} ${reldir} ' + unique))"
|
||||
OUTPUT_VARIABLE _target OUTPUT_STRIP_TRAILING_WHITESPACE)
|
||||
add_custom_target(${_target} ALL DEPENDS ${ARGN})
|
||||
endfunction(GR_UNIQUE_TARGET)
|
||||
|
||||
########################################################################
|
||||
# Install python sources (also builds and installs byte-compiled python)
|
||||
########################################################################
|
||||
function(GR_PYTHON_INSTALL)
|
||||
include(CMakeParseArgumentsCopy)
|
||||
CMAKE_PARSE_ARGUMENTS(GR_PYTHON_INSTALL "" "DESTINATION;COMPONENT" "FILES;PROGRAMS" ${ARGN})
|
||||
|
||||
####################################################################
|
||||
if(GR_PYTHON_INSTALL_FILES)
|
||||
####################################################################
|
||||
install(${ARGN}) #installs regular python files
|
||||
|
||||
#create a list of all generated files
|
||||
unset(pysrcfiles)
|
||||
unset(pycfiles)
|
||||
unset(pyofiles)
|
||||
foreach(pyfile ${GR_PYTHON_INSTALL_FILES})
|
||||
get_filename_component(pyfile ${pyfile} ABSOLUTE)
|
||||
list(APPEND pysrcfiles ${pyfile})
|
||||
|
||||
#determine if this file is in the source or binary directory
|
||||
file(RELATIVE_PATH source_rel_path ${CMAKE_CURRENT_SOURCE_DIR} ${pyfile})
|
||||
string(LENGTH "${source_rel_path}" source_rel_path_len)
|
||||
file(RELATIVE_PATH binary_rel_path ${CMAKE_CURRENT_BINARY_DIR} ${pyfile})
|
||||
string(LENGTH "${binary_rel_path}" binary_rel_path_len)
|
||||
|
||||
#and set the generated path appropriately
|
||||
if(${source_rel_path_len} GREATER ${binary_rel_path_len})
|
||||
set(pygenfile ${CMAKE_CURRENT_BINARY_DIR}/${binary_rel_path})
|
||||
else()
|
||||
set(pygenfile ${CMAKE_CURRENT_BINARY_DIR}/${source_rel_path})
|
||||
endif()
|
||||
list(APPEND pycfiles ${pygenfile}c)
|
||||
list(APPEND pyofiles ${pygenfile}o)
|
||||
|
||||
#ensure generation path exists
|
||||
get_filename_component(pygen_path ${pygenfile} PATH)
|
||||
file(MAKE_DIRECTORY ${pygen_path})
|
||||
|
||||
endforeach(pyfile)
|
||||
|
||||
#the command to generate the pyc files
|
||||
add_custom_command(
|
||||
DEPENDS ${pysrcfiles} OUTPUT ${pycfiles}
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${CMAKE_BINARY_DIR}/python_compile_helper.py ${pysrcfiles} ${pycfiles}
|
||||
)
|
||||
|
||||
#the command to generate the pyo files
|
||||
add_custom_command(
|
||||
DEPENDS ${pysrcfiles} OUTPUT ${pyofiles}
|
||||
COMMAND ${PYTHON_EXECUTABLE} -O ${CMAKE_BINARY_DIR}/python_compile_helper.py ${pysrcfiles} ${pyofiles}
|
||||
)
|
||||
|
||||
#create install rule and add generated files to target list
|
||||
set(python_install_gen_targets ${pycfiles} ${pyofiles})
|
||||
install(FILES ${python_install_gen_targets}
|
||||
DESTINATION ${GR_PYTHON_INSTALL_DESTINATION}
|
||||
COMPONENT ${GR_PYTHON_INSTALL_COMPONENT}
|
||||
)
|
||||
|
||||
####################################################################
|
||||
elseif(GR_PYTHON_INSTALL_PROGRAMS)
|
||||
####################################################################
|
||||
file(TO_NATIVE_PATH ${PYTHON_EXECUTABLE} pyexe_native)
|
||||
|
||||
if (CMAKE_CROSSCOMPILING)
|
||||
set(pyexe_native "/usr/bin/env python")
|
||||
endif()
|
||||
|
||||
foreach(pyfile ${GR_PYTHON_INSTALL_PROGRAMS})
|
||||
get_filename_component(pyfile_name ${pyfile} NAME)
|
||||
get_filename_component(pyfile ${pyfile} ABSOLUTE)
|
||||
string(REPLACE "${CMAKE_SOURCE_DIR}" "${CMAKE_BINARY_DIR}" pyexefile "${pyfile}.exe")
|
||||
list(APPEND python_install_gen_targets ${pyexefile})
|
||||
|
||||
get_filename_component(pyexefile_path ${pyexefile} PATH)
|
||||
file(MAKE_DIRECTORY ${pyexefile_path})
|
||||
|
||||
add_custom_command(
|
||||
OUTPUT ${pyexefile} DEPENDS ${pyfile}
|
||||
COMMAND ${PYTHON_EXECUTABLE} -c
|
||||
"import re; R=re.compile('^\#!.*$\\n',flags=re.MULTILINE); open('${pyexefile}','w').write('\#!${pyexe_native}\\n'+R.sub('',open('${pyfile}','r').read()))"
|
||||
COMMENT "Shebangin ${pyfile_name}"
|
||||
VERBATIM
|
||||
)
|
||||
|
||||
#on windows, python files need an extension to execute
|
||||
get_filename_component(pyfile_ext ${pyfile} EXT)
|
||||
if(WIN32 AND NOT pyfile_ext)
|
||||
set(pyfile_name "${pyfile_name}.py")
|
||||
endif()
|
||||
|
||||
install(PROGRAMS ${pyexefile} RENAME ${pyfile_name}
|
||||
DESTINATION ${GR_PYTHON_INSTALL_DESTINATION}
|
||||
COMPONENT ${GR_PYTHON_INSTALL_COMPONENT}
|
||||
)
|
||||
endforeach(pyfile)
|
||||
|
||||
endif()
|
||||
|
||||
GR_UNIQUE_TARGET("pygen" ${python_install_gen_targets})
|
||||
|
||||
endfunction(GR_PYTHON_INSTALL)
|
||||
|
||||
########################################################################
|
||||
# Write the python helper script that generates byte code files
|
||||
########################################################################
|
||||
file(WRITE ${CMAKE_BINARY_DIR}/python_compile_helper.py "
|
||||
import sys, py_compile
|
||||
files = sys.argv[1:]
|
||||
srcs, gens = files[:len(files)/2], files[len(files)/2:]
|
||||
for src, gen in zip(srcs, gens):
|
||||
py_compile.compile(file=src, cfile=gen, doraise=True)
|
||||
")
|
|
@ -0,0 +1,251 @@
|
|||
# Copyright 2010-2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
if(DEFINED __INCLUDED_GR_SWIG_CMAKE)
|
||||
return()
|
||||
endif()
|
||||
set(__INCLUDED_GR_SWIG_CMAKE TRUE)
|
||||
|
||||
include(GrPython)
|
||||
|
||||
########################################################################
|
||||
# Builds a swig documentation file to be generated into python docstrings
|
||||
# Usage: GR_SWIG_MAKE_DOCS(output_file input_path input_path....)
|
||||
#
|
||||
# Set the following variable to specify extra dependent targets:
|
||||
# - GR_SWIG_DOCS_SOURCE_DEPS
|
||||
# - GR_SWIG_DOCS_TARGET_DEPS
|
||||
########################################################################
|
||||
function(GR_SWIG_MAKE_DOCS output_file)
|
||||
if(ENABLE_DOXYGEN)
|
||||
|
||||
#setup the input files variable list, quote formated
|
||||
set(input_files)
|
||||
unset(INPUT_PATHS)
|
||||
foreach(input_path ${ARGN})
|
||||
if(IS_DIRECTORY ${input_path}) #when input path is a directory
|
||||
file(GLOB input_path_h_files ${input_path}/*.h)
|
||||
else() #otherwise its just a file, no glob
|
||||
set(input_path_h_files ${input_path})
|
||||
endif()
|
||||
list(APPEND input_files ${input_path_h_files})
|
||||
set(INPUT_PATHS "${INPUT_PATHS} \"${input_path}\"")
|
||||
endforeach(input_path)
|
||||
|
||||
#determine the output directory
|
||||
get_filename_component(name ${output_file} NAME_WE)
|
||||
get_filename_component(OUTPUT_DIRECTORY ${output_file} PATH)
|
||||
set(OUTPUT_DIRECTORY ${OUTPUT_DIRECTORY}/${name}_swig_docs)
|
||||
make_directory(${OUTPUT_DIRECTORY})
|
||||
|
||||
#generate the Doxyfile used by doxygen
|
||||
configure_file(
|
||||
${CMAKE_SOURCE_DIR}/docs/doxygen/Doxyfile.swig_doc.in
|
||||
${OUTPUT_DIRECTORY}/Doxyfile
|
||||
@ONLY)
|
||||
|
||||
#Create a dummy custom command that depends on other targets
|
||||
include(GrMiscUtils)
|
||||
GR_GEN_TARGET_DEPS(_${name}_tag tag_deps ${GR_SWIG_DOCS_TARGET_DEPS})
|
||||
|
||||
#call doxygen on the Doxyfile + input headers
|
||||
add_custom_command(
|
||||
OUTPUT ${OUTPUT_DIRECTORY}/xml/index.xml
|
||||
DEPENDS ${input_files} ${GR_SWIG_DOCS_SOURCE_DEPS} ${tag_deps}
|
||||
COMMAND ${DOXYGEN_EXECUTABLE} ${OUTPUT_DIRECTORY}/Doxyfile
|
||||
COMMENT "Generating doxygen xml for ${name} docs"
|
||||
)
|
||||
|
||||
#call the swig_doc script on the xml files
|
||||
add_custom_command(
|
||||
OUTPUT ${output_file}
|
||||
DEPENDS ${input_files} ${stamp-file} ${OUTPUT_DIRECTORY}/xml/index.xml
|
||||
COMMAND ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B}
|
||||
${CMAKE_SOURCE_DIR}/docs/doxygen/swig_doc.py
|
||||
${OUTPUT_DIRECTORY}/xml
|
||||
${output_file}
|
||||
COMMENT "Generating python docstrings for ${name}"
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/docs/doxygen
|
||||
)
|
||||
|
||||
else(ENABLE_DOXYGEN)
|
||||
file(WRITE ${output_file} "\n") #no doxygen -> empty file
|
||||
endif(ENABLE_DOXYGEN)
|
||||
endfunction(GR_SWIG_MAKE_DOCS)
|
||||
|
||||
########################################################################
|
||||
# Build a swig target for the common gnuradio use case. Usage:
|
||||
# GR_SWIG_MAKE(target ifile ifile ifile...)
|
||||
#
|
||||
# Set the following variables before calling:
|
||||
# - GR_SWIG_FLAGS
|
||||
# - GR_SWIG_INCLUDE_DIRS
|
||||
# - GR_SWIG_LIBRARIES
|
||||
# - GR_SWIG_SOURCE_DEPS
|
||||
# - GR_SWIG_TARGET_DEPS
|
||||
# - GR_SWIG_DOC_FILE
|
||||
# - GR_SWIG_DOC_DIRS
|
||||
########################################################################
|
||||
macro(GR_SWIG_MAKE name)
|
||||
set(ifiles ${ARGN})
|
||||
|
||||
# Shimming this in here to take care of a SWIG bug with handling
|
||||
# vector<size_t> and vector<unsigned int> (on 32-bit machines) and
|
||||
# vector<long unsigned int> (on 64-bit machines). Use this to test
|
||||
# the size of size_t, then set SIZE_T_32 if it's a 32-bit machine
|
||||
# or not if it's 64-bit. The logic in gr_type.i handles the rest.
|
||||
INCLUDE(CheckTypeSize)
|
||||
CHECK_TYPE_SIZE("size_t" SIZEOF_SIZE_T)
|
||||
CHECK_TYPE_SIZE("unsigned int" SIZEOF_UINT)
|
||||
if(${SIZEOF_SIZE_T} EQUAL ${SIZEOF_UINT})
|
||||
list(APPEND GR_SWIG_FLAGS -DSIZE_T_32)
|
||||
endif(${SIZEOF_SIZE_T} EQUAL ${SIZEOF_UINT})
|
||||
|
||||
#do swig doc generation if specified
|
||||
if(GR_SWIG_DOC_FILE)
|
||||
set(GR_SWIG_DOCS_SOURCE_DEPS ${GR_SWIG_SOURCE_DEPS})
|
||||
list(APPEND GR_SWIG_DOCS_TARGET_DEPS ${GR_SWIG_TARGET_DEPS})
|
||||
GR_SWIG_MAKE_DOCS(${GR_SWIG_DOC_FILE} ${GR_SWIG_DOC_DIRS})
|
||||
add_custom_target(${name}_swig_doc DEPENDS ${GR_SWIG_DOC_FILE})
|
||||
list(APPEND GR_SWIG_TARGET_DEPS ${name}_swig_doc ${GR_RUNTIME_SWIG_DOC_FILE})
|
||||
endif()
|
||||
|
||||
#append additional include directories
|
||||
find_package(PythonLibs 2)
|
||||
list(APPEND GR_SWIG_INCLUDE_DIRS ${PYTHON_INCLUDE_PATH}) #deprecated name (now dirs)
|
||||
list(APPEND GR_SWIG_INCLUDE_DIRS ${PYTHON_INCLUDE_DIRS})
|
||||
|
||||
#prepend local swig directories
|
||||
list(INSERT GR_SWIG_INCLUDE_DIRS 0 ${CMAKE_CURRENT_SOURCE_DIR})
|
||||
list(INSERT GR_SWIG_INCLUDE_DIRS 0 ${CMAKE_CURRENT_BINARY_DIR})
|
||||
|
||||
#determine include dependencies for swig file
|
||||
execute_process(
|
||||
COMMAND ${PYTHON_EXECUTABLE}
|
||||
${CMAKE_BINARY_DIR}/get_swig_deps.py
|
||||
"${ifiles}" "${GR_SWIG_INCLUDE_DIRS}"
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
OUTPUT_VARIABLE SWIG_MODULE_${name}_EXTRA_DEPS
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
|
||||
)
|
||||
|
||||
#Create a dummy custom command that depends on other targets
|
||||
include(GrMiscUtils)
|
||||
GR_GEN_TARGET_DEPS(_${name}_swig_tag tag_deps ${GR_SWIG_TARGET_DEPS})
|
||||
set(tag_file ${CMAKE_CURRENT_BINARY_DIR}/${name}.tag)
|
||||
add_custom_command(
|
||||
OUTPUT ${tag_file}
|
||||
DEPENDS ${GR_SWIG_SOURCE_DEPS} ${tag_deps}
|
||||
COMMAND ${CMAKE_COMMAND} -E touch ${tag_file}
|
||||
)
|
||||
|
||||
#append the specified include directories
|
||||
include_directories(${GR_SWIG_INCLUDE_DIRS})
|
||||
list(APPEND SWIG_MODULE_${name}_EXTRA_DEPS ${tag_file})
|
||||
|
||||
#setup the swig flags with flags and include directories
|
||||
set(CMAKE_SWIG_FLAGS -fvirtual -modern -keyword -w511 -module ${name} ${GR_SWIG_FLAGS})
|
||||
foreach(dir ${GR_SWIG_INCLUDE_DIRS})
|
||||
list(APPEND CMAKE_SWIG_FLAGS "-I${dir}")
|
||||
endforeach(dir)
|
||||
|
||||
#set the C++ property on the swig .i file so it builds
|
||||
set_source_files_properties(${ifiles} PROPERTIES CPLUSPLUS ON)
|
||||
|
||||
#setup the actual swig library target to be built
|
||||
include(UseSWIG)
|
||||
SWIG_ADD_MODULE(${name} python ${ifiles})
|
||||
SWIG_LINK_LIBRARIES(${name} ${PYTHON_LIBRARIES} ${GR_SWIG_LIBRARIES})
|
||||
if(${name} STREQUAL "runtime_swig")
|
||||
SET_TARGET_PROPERTIES(${SWIG_MODULE_runtime_swig_REAL_NAME} PROPERTIES DEFINE_SYMBOL "gnuradio_runtime_EXPORTS")
|
||||
endif(${name} STREQUAL "runtime_swig")
|
||||
|
||||
endmacro(GR_SWIG_MAKE)
|
||||
|
||||
########################################################################
|
||||
# Install swig targets generated by GR_SWIG_MAKE. Usage:
|
||||
# GR_SWIG_INSTALL(
|
||||
# TARGETS target target target...
|
||||
# [DESTINATION destination]
|
||||
# [COMPONENT component]
|
||||
# )
|
||||
########################################################################
|
||||
macro(GR_SWIG_INSTALL)
|
||||
|
||||
include(CMakeParseArgumentsCopy)
|
||||
CMAKE_PARSE_ARGUMENTS(GR_SWIG_INSTALL "" "DESTINATION;COMPONENT" "TARGETS" ${ARGN})
|
||||
|
||||
foreach(name ${GR_SWIG_INSTALL_TARGETS})
|
||||
install(TARGETS ${SWIG_MODULE_${name}_REAL_NAME}
|
||||
DESTINATION ${GR_SWIG_INSTALL_DESTINATION}
|
||||
COMPONENT ${GR_SWIG_INSTALL_COMPONENT}
|
||||
)
|
||||
|
||||
include(GrPython)
|
||||
GR_PYTHON_INSTALL(FILES ${CMAKE_CURRENT_BINARY_DIR}/${name}.py
|
||||
DESTINATION ${GR_SWIG_INSTALL_DESTINATION}
|
||||
COMPONENT ${GR_SWIG_INSTALL_COMPONENT}
|
||||
)
|
||||
|
||||
GR_LIBTOOL(
|
||||
TARGET ${SWIG_MODULE_${name}_REAL_NAME}
|
||||
DESTINATION ${GR_SWIG_INSTALL_DESTINATION}
|
||||
)
|
||||
|
||||
endforeach(name)
|
||||
|
||||
endmacro(GR_SWIG_INSTALL)
|
||||
|
||||
########################################################################
|
||||
# Generate a python file that can determine swig dependencies.
|
||||
# Used by the make macro above to determine extra dependencies.
|
||||
# When you build C++, CMake figures out the header dependencies.
|
||||
# This code essentially performs that logic for swig includes.
|
||||
########################################################################
|
||||
file(WRITE ${CMAKE_BINARY_DIR}/get_swig_deps.py "
|
||||
|
||||
import os, sys, re
|
||||
|
||||
i_include_matcher = re.compile('%(include|import)\\s*[<|\"](.*)[>|\"]')
|
||||
h_include_matcher = re.compile('#(include)\\s*[<|\"](.*)[>|\"]')
|
||||
include_dirs = sys.argv[2].split(';')
|
||||
|
||||
def get_swig_incs(file_path):
|
||||
if file_path.endswith('.i'): matcher = i_include_matcher
|
||||
else: matcher = h_include_matcher
|
||||
file_contents = open(file_path, 'r').read()
|
||||
return matcher.findall(file_contents, re.MULTILINE)
|
||||
|
||||
def get_swig_deps(file_path, level):
|
||||
deps = [file_path]
|
||||
if level == 0: return deps
|
||||
for keyword, inc_file in get_swig_incs(file_path):
|
||||
for inc_dir in include_dirs:
|
||||
inc_path = os.path.join(inc_dir, inc_file)
|
||||
if not os.path.exists(inc_path): continue
|
||||
deps.extend(get_swig_deps(inc_path, level-1))
|
||||
break #found, we dont search in lower prio inc dirs
|
||||
return deps
|
||||
|
||||
if __name__ == '__main__':
|
||||
ifiles = sys.argv[1].split(';')
|
||||
deps = sum([get_swig_deps(ifile, 3) for ifile in ifiles], [])
|
||||
#sys.stderr.write(';'.join(set(deps)) + '\\n\\n')
|
||||
print(';'.join(set(deps)))
|
||||
")
|
|
@ -0,0 +1,143 @@
|
|||
# Copyright 2010-2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
if(DEFINED __INCLUDED_GR_TEST_CMAKE)
|
||||
return()
|
||||
endif()
|
||||
set(__INCLUDED_GR_TEST_CMAKE TRUE)
|
||||
|
||||
########################################################################
|
||||
# Add a unit test and setup the environment for a unit test.
|
||||
# Takes the same arguments as the ADD_TEST function.
|
||||
#
|
||||
# Before calling set the following variables:
|
||||
# GR_TEST_TARGET_DEPS - built targets for the library path
|
||||
# GR_TEST_LIBRARY_DIRS - directories for the library path
|
||||
# GR_TEST_PYTHON_DIRS - directories for the python path
|
||||
# GR_TEST_ENVIRONS - other environment key/value pairs
|
||||
########################################################################
|
||||
function(GR_ADD_TEST test_name)
|
||||
|
||||
#Ensure that the build exe also appears in the PATH.
|
||||
list(APPEND GR_TEST_TARGET_DEPS ${ARGN})
|
||||
|
||||
#In the land of windows, all libraries must be in the PATH.
|
||||
#Since the dependent libraries are not yet installed,
|
||||
#we must manually set them in the PATH to run tests.
|
||||
#The following appends the path of a target dependency.
|
||||
foreach(target ${GR_TEST_TARGET_DEPS})
|
||||
get_target_property(location ${target} LOCATION)
|
||||
if(location)
|
||||
get_filename_component(path ${location} PATH)
|
||||
string(REGEX REPLACE "\\$\\(.*\\)" ${CMAKE_BUILD_TYPE} path ${path})
|
||||
list(APPEND GR_TEST_LIBRARY_DIRS ${path})
|
||||
endif(location)
|
||||
endforeach(target)
|
||||
|
||||
if(WIN32)
|
||||
#SWIG generates the python library files into a subdirectory.
|
||||
#Therefore, we must append this subdirectory into PYTHONPATH.
|
||||
#Only do this for the python directories matching the following:
|
||||
foreach(pydir ${GR_TEST_PYTHON_DIRS})
|
||||
get_filename_component(name ${pydir} NAME)
|
||||
if(name MATCHES "^(swig|lib|src)$")
|
||||
list(APPEND GR_TEST_PYTHON_DIRS ${pydir}/${CMAKE_BUILD_TYPE})
|
||||
endif()
|
||||
endforeach(pydir)
|
||||
endif(WIN32)
|
||||
|
||||
file(TO_NATIVE_PATH ${CMAKE_CURRENT_SOURCE_DIR} srcdir)
|
||||
file(TO_NATIVE_PATH "${GR_TEST_LIBRARY_DIRS}" libpath) #ok to use on dir list?
|
||||
file(TO_NATIVE_PATH "${GR_TEST_PYTHON_DIRS}" pypath) #ok to use on dir list?
|
||||
|
||||
set(environs "VOLK_GENERIC=1" "GR_DONT_LOAD_PREFS=1" "srcdir=${srcdir}")
|
||||
list(APPEND environs ${GR_TEST_ENVIRONS})
|
||||
|
||||
#http://www.cmake.org/pipermail/cmake/2009-May/029464.html
|
||||
#Replaced this add test + set environs code with the shell script generation.
|
||||
#Its nicer to be able to manually run the shell script to diagnose problems.
|
||||
#ADD_TEST(${ARGV})
|
||||
#SET_TESTS_PROPERTIES(${test_name} PROPERTIES ENVIRONMENT "${environs}")
|
||||
|
||||
if(UNIX)
|
||||
set(LD_PATH_VAR "LD_LIBRARY_PATH")
|
||||
if(APPLE)
|
||||
set(LD_PATH_VAR "DYLD_LIBRARY_PATH")
|
||||
endif()
|
||||
|
||||
set(binpath "${CMAKE_CURRENT_BINARY_DIR}:$PATH")
|
||||
list(APPEND libpath "$${LD_PATH_VAR}")
|
||||
list(APPEND pypath "$PYTHONPATH")
|
||||
|
||||
#replace list separator with the path separator
|
||||
string(REPLACE ";" ":" libpath "${libpath}")
|
||||
string(REPLACE ";" ":" pypath "${pypath}")
|
||||
list(APPEND environs "PATH=${binpath}" "${LD_PATH_VAR}=${libpath}" "PYTHONPATH=${pypath}")
|
||||
|
||||
#generate a bat file that sets the environment and runs the test
|
||||
if (CMAKE_CROSSCOMPILING)
|
||||
set(SHELL "/bin/sh")
|
||||
else(CMAKE_CROSSCOMPILING)
|
||||
find_program(SHELL sh)
|
||||
endif(CMAKE_CROSSCOMPILING)
|
||||
set(sh_file ${CMAKE_CURRENT_BINARY_DIR}/${test_name}_test.sh)
|
||||
file(WRITE ${sh_file} "#!${SHELL}\n")
|
||||
#each line sets an environment variable
|
||||
foreach(environ ${environs})
|
||||
file(APPEND ${sh_file} "export ${environ}\n")
|
||||
endforeach(environ)
|
||||
#load the command to run with its arguments
|
||||
foreach(arg ${ARGN})
|
||||
file(APPEND ${sh_file} "${arg} ")
|
||||
endforeach(arg)
|
||||
file(APPEND ${sh_file} "\n")
|
||||
|
||||
#make the shell file executable
|
||||
execute_process(COMMAND chmod +x ${sh_file})
|
||||
|
||||
add_test(${test_name} ${SHELL} ${sh_file})
|
||||
|
||||
endif(UNIX)
|
||||
|
||||
if(WIN32)
|
||||
list(APPEND libpath ${DLL_PATHS} "%PATH%")
|
||||
list(APPEND pypath "%PYTHONPATH%")
|
||||
|
||||
#replace list separator with the path separator (escaped)
|
||||
string(REPLACE ";" "\\;" libpath "${libpath}")
|
||||
string(REPLACE ";" "\\;" pypath "${pypath}")
|
||||
list(APPEND environs "PATH=${libpath}" "PYTHONPATH=${pypath}")
|
||||
|
||||
#generate a bat file that sets the environment and runs the test
|
||||
set(bat_file ${CMAKE_CURRENT_BINARY_DIR}/${test_name}_test.bat)
|
||||
file(WRITE ${bat_file} "@echo off\n")
|
||||
#each line sets an environment variable
|
||||
foreach(environ ${environs})
|
||||
file(APPEND ${bat_file} "SET ${environ}\n")
|
||||
endforeach(environ)
|
||||
#load the command to run with its arguments
|
||||
foreach(arg ${ARGN})
|
||||
file(APPEND ${bat_file} "${arg} ")
|
||||
endforeach(arg)
|
||||
file(APPEND ${bat_file} "\n")
|
||||
|
||||
add_test(${test_name} ${bat_file})
|
||||
endif(WIN32)
|
||||
|
||||
endfunction(GR_ADD_TEST)
|
|
@ -0,0 +1,304 @@
|
|||
# - SWIG module for CMake
|
||||
# Defines the following macros:
|
||||
# SWIG_ADD_MODULE(name language [ files ])
|
||||
# - Define swig module with given name and specified language
|
||||
# SWIG_LINK_LIBRARIES(name [ libraries ])
|
||||
# - Link libraries to swig module
|
||||
# All other macros are for internal use only.
|
||||
# To get the actual name of the swig module,
|
||||
# use: ${SWIG_MODULE_${name}_REAL_NAME}.
|
||||
# Set Source files properties such as CPLUSPLUS and SWIG_FLAGS to specify
|
||||
# special behavior of SWIG. Also global CMAKE_SWIG_FLAGS can be used to add
|
||||
# special flags to all swig calls.
|
||||
# Another special variable is CMAKE_SWIG_OUTDIR, it allows one to specify
|
||||
# where to write all the swig generated module (swig -outdir option)
|
||||
# The name-specific variable SWIG_MODULE_<name>_EXTRA_DEPS may be used
|
||||
# to specify extra dependencies for the generated modules.
|
||||
# If the source file generated by swig need some special flag you can use
|
||||
# set_source_files_properties( ${swig_generated_file_fullname}
|
||||
# PROPERTIES COMPILE_FLAGS "-bla")
|
||||
|
||||
|
||||
#=============================================================================
|
||||
# Copyright 2004-2009 Kitware, Inc.
|
||||
# Copyright 2009 Mathieu Malaterre <mathieu.malaterre@gmail.com>
|
||||
#
|
||||
# Distributed under the OSI-approved BSD License (the "License");
|
||||
# see accompanying file Copyright.txt for details.
|
||||
#
|
||||
# This software is distributed WITHOUT ANY WARRANTY; without even the
|
||||
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
# See the License for more information.
|
||||
#=============================================================================
|
||||
# (To distribute this file outside of CMake, substitute the full
|
||||
# License text for the above reference.)
|
||||
|
||||
set(SWIG_CXX_EXTENSION "cxx")
|
||||
set(SWIG_EXTRA_LIBRARIES "")
|
||||
|
||||
set(SWIG_PYTHON_EXTRA_FILE_EXTENSION "py")
|
||||
|
||||
#
|
||||
# For given swig module initialize variables associated with it
|
||||
#
|
||||
macro(SWIG_MODULE_INITIALIZE name language)
|
||||
string(TOUPPER "${language}" swig_uppercase_language)
|
||||
string(TOLOWER "${language}" swig_lowercase_language)
|
||||
set(SWIG_MODULE_${name}_LANGUAGE "${swig_uppercase_language}")
|
||||
set(SWIG_MODULE_${name}_SWIG_LANGUAGE_FLAG "${swig_lowercase_language}")
|
||||
|
||||
set(SWIG_MODULE_${name}_REAL_NAME "${name}")
|
||||
if("${SWIG_MODULE_${name}_LANGUAGE}" STREQUAL "UNKNOWN")
|
||||
message(FATAL_ERROR "SWIG Error: Language \"${language}\" not found")
|
||||
elseif("${SWIG_MODULE_${name}_LANGUAGE}" STREQUAL "PYTHON")
|
||||
# when swig is used without the -interface it will produce in the module.py
|
||||
# a 'import _modulename' statement, which implies having a corresponding
|
||||
# _modulename.so (*NIX), _modulename.pyd (Win32).
|
||||
set(SWIG_MODULE_${name}_REAL_NAME "_${name}")
|
||||
elseif("${SWIG_MODULE_${name}_LANGUAGE}" STREQUAL "PERL")
|
||||
set(SWIG_MODULE_${name}_EXTRA_FLAGS "-shadow")
|
||||
endif()
|
||||
endmacro()
|
||||
|
||||
#
|
||||
# For a given language, input file, and output file, determine extra files that
|
||||
# will be generated. This is internal swig macro.
|
||||
#
|
||||
|
||||
macro(SWIG_GET_EXTRA_OUTPUT_FILES language outfiles generatedpath infile)
|
||||
set(${outfiles} "")
|
||||
get_source_file_property(SWIG_GET_EXTRA_OUTPUT_FILES_module_basename
|
||||
${infile} SWIG_MODULE_NAME)
|
||||
if(SWIG_GET_EXTRA_OUTPUT_FILES_module_basename STREQUAL "NOTFOUND")
|
||||
get_filename_component(SWIG_GET_EXTRA_OUTPUT_FILES_module_basename "${infile}" NAME_WE)
|
||||
endif()
|
||||
foreach(it ${SWIG_${language}_EXTRA_FILE_EXTENSION})
|
||||
set(${outfiles} ${${outfiles}}
|
||||
"${generatedpath}/${SWIG_GET_EXTRA_OUTPUT_FILES_module_basename}.${it}")
|
||||
endforeach()
|
||||
endmacro()
|
||||
|
||||
#
|
||||
# Take swig (*.i) file and add proper custom commands for it
|
||||
#
|
||||
macro(SWIG_ADD_SOURCE_TO_MODULE name outfiles infile)
|
||||
set(swig_full_infile ${infile})
|
||||
get_filename_component(swig_source_file_path "${infile}" PATH)
|
||||
get_filename_component(swig_source_file_name_we "${infile}" NAME_WE)
|
||||
get_source_file_property(swig_source_file_generated ${infile} GENERATED)
|
||||
get_source_file_property(swig_source_file_cplusplus ${infile} CPLUSPLUS)
|
||||
get_source_file_property(swig_source_file_flags ${infile} SWIG_FLAGS)
|
||||
if("${swig_source_file_flags}" STREQUAL "NOTFOUND")
|
||||
set(swig_source_file_flags "")
|
||||
endif()
|
||||
set(swig_source_file_fullname "${infile}")
|
||||
if(${swig_source_file_path} MATCHES "^${CMAKE_CURRENT_SOURCE_DIR}")
|
||||
string(REGEX REPLACE
|
||||
"^${CMAKE_CURRENT_SOURCE_DIR}" ""
|
||||
swig_source_file_relative_path
|
||||
"${swig_source_file_path}")
|
||||
else()
|
||||
if(${swig_source_file_path} MATCHES "^${CMAKE_CURRENT_BINARY_DIR}")
|
||||
string(REGEX REPLACE
|
||||
"^${CMAKE_CURRENT_BINARY_DIR}" ""
|
||||
swig_source_file_relative_path
|
||||
"${swig_source_file_path}")
|
||||
set(swig_source_file_generated 1)
|
||||
else()
|
||||
set(swig_source_file_relative_path "${swig_source_file_path}")
|
||||
if(swig_source_file_generated)
|
||||
set(swig_source_file_fullname "${CMAKE_CURRENT_BINARY_DIR}/${infile}")
|
||||
else()
|
||||
set(swig_source_file_fullname "${CMAKE_CURRENT_SOURCE_DIR}/${infile}")
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
set(swig_generated_file_fullname
|
||||
"${CMAKE_CURRENT_BINARY_DIR}")
|
||||
if(swig_source_file_relative_path)
|
||||
set(swig_generated_file_fullname
|
||||
"${swig_generated_file_fullname}/${swig_source_file_relative_path}")
|
||||
endif()
|
||||
# If CMAKE_SWIG_OUTDIR was specified then pass it to -outdir
|
||||
if(CMAKE_SWIG_OUTDIR)
|
||||
set(swig_outdir ${CMAKE_SWIG_OUTDIR})
|
||||
else()
|
||||
set(swig_outdir ${CMAKE_CURRENT_BINARY_DIR})
|
||||
endif()
|
||||
SWIG_GET_EXTRA_OUTPUT_FILES(${SWIG_MODULE_${name}_LANGUAGE}
|
||||
swig_extra_generated_files
|
||||
"${swig_outdir}"
|
||||
"${infile}")
|
||||
set(swig_generated_file_fullname
|
||||
"${swig_generated_file_fullname}/${swig_source_file_name_we}")
|
||||
# add the language into the name of the file (i.e. TCL_wrap)
|
||||
# this allows for the same .i file to be wrapped into different languages
|
||||
set(swig_generated_file_fullname
|
||||
"${swig_generated_file_fullname}${SWIG_MODULE_${name}_LANGUAGE}_wrap")
|
||||
|
||||
if(swig_source_file_cplusplus)
|
||||
set(swig_generated_file_fullname
|
||||
"${swig_generated_file_fullname}.${SWIG_CXX_EXTENSION}")
|
||||
else()
|
||||
set(swig_generated_file_fullname
|
||||
"${swig_generated_file_fullname}.c")
|
||||
endif()
|
||||
|
||||
# Shut up some warnings from poor SWIG code generation that we
|
||||
# can do nothing about, when this flag is available
|
||||
include(CheckCXXCompilerFlag)
|
||||
check_cxx_compiler_flag("-Wno-unused-but-set-variable" HAVE_WNO_UNUSED_BUT_SET_VARIABLE)
|
||||
if(HAVE_WNO_UNUSED_BUT_SET_VARIABLE)
|
||||
set_source_files_properties(${swig_generated_file_fullname}
|
||||
PROPERTIES COMPILE_FLAGS "-Wno-unused-but-set-variable")
|
||||
endif(HAVE_WNO_UNUSED_BUT_SET_VARIABLE)
|
||||
|
||||
get_directory_property(cmake_include_directories INCLUDE_DIRECTORIES)
|
||||
set(swig_include_dirs)
|
||||
foreach(it ${cmake_include_directories})
|
||||
set(swig_include_dirs ${swig_include_dirs} "-I${it}")
|
||||
endforeach()
|
||||
|
||||
set(swig_special_flags)
|
||||
# default is c, so add c++ flag if it is c++
|
||||
if(swig_source_file_cplusplus)
|
||||
set(swig_special_flags ${swig_special_flags} "-c++")
|
||||
endif()
|
||||
set(swig_extra_flags)
|
||||
if(SWIG_MODULE_${name}_EXTRA_FLAGS)
|
||||
set(swig_extra_flags ${swig_extra_flags} ${SWIG_MODULE_${name}_EXTRA_FLAGS})
|
||||
endif()
|
||||
|
||||
# hack to work around CMake bug in add_custom_command with multiple OUTPUT files
|
||||
|
||||
file(RELATIVE_PATH reldir ${CMAKE_BINARY_DIR} ${CMAKE_CURRENT_BINARY_DIR})
|
||||
execute_process(
|
||||
COMMAND ${PYTHON_EXECUTABLE} -c "import re, hashlib
|
||||
unique = hashlib.md5('${reldir}${ARGN}').hexdigest()[:5]
|
||||
print(re.sub('\\W', '_', '${name} ${reldir} ' + unique))"
|
||||
OUTPUT_VARIABLE _target OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
)
|
||||
|
||||
file(
|
||||
WRITE ${CMAKE_CURRENT_BINARY_DIR}/${_target}.cpp.in
|
||||
"int main(void){return 0;}\n"
|
||||
)
|
||||
|
||||
# create dummy dependencies
|
||||
add_custom_command(
|
||||
OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${_target}.cpp
|
||||
COMMAND ${CMAKE_COMMAND} -E copy
|
||||
${CMAKE_CURRENT_BINARY_DIR}/${_target}.cpp.in
|
||||
${CMAKE_CURRENT_BINARY_DIR}/${_target}.cpp
|
||||
DEPENDS "${swig_source_file_fullname}" ${SWIG_MODULE_${name}_EXTRA_DEPS}
|
||||
COMMENT ""
|
||||
)
|
||||
|
||||
# create the dummy target
|
||||
add_executable(${_target} ${CMAKE_CURRENT_BINARY_DIR}/${_target}.cpp)
|
||||
|
||||
# add a custom command to the dummy target
|
||||
add_custom_command(
|
||||
TARGET ${_target}
|
||||
# Let's create the ${swig_outdir} at execution time, in case dir contains $(OutDir)
|
||||
COMMAND ${CMAKE_COMMAND} -E make_directory ${swig_outdir}
|
||||
COMMAND "${SWIG_EXECUTABLE}"
|
||||
ARGS "-${SWIG_MODULE_${name}_SWIG_LANGUAGE_FLAG}"
|
||||
${swig_source_file_flags}
|
||||
${CMAKE_SWIG_FLAGS}
|
||||
-outdir ${swig_outdir}
|
||||
${swig_special_flags}
|
||||
${swig_extra_flags}
|
||||
${swig_include_dirs}
|
||||
-o "${swig_generated_file_fullname}"
|
||||
"${swig_source_file_fullname}"
|
||||
COMMENT "Swig source"
|
||||
)
|
||||
|
||||
#add dummy independent dependencies from the _target to each file
|
||||
#that will be generated by the SWIG command above
|
||||
|
||||
set(${outfiles} "${swig_generated_file_fullname}" ${swig_extra_generated_files})
|
||||
|
||||
foreach(swig_gen_file ${${outfiles}})
|
||||
add_custom_command(
|
||||
OUTPUT ${swig_gen_file}
|
||||
COMMAND ""
|
||||
DEPENDS ${_target}
|
||||
COMMENT ""
|
||||
)
|
||||
endforeach()
|
||||
|
||||
set_source_files_properties(
|
||||
${outfiles} PROPERTIES GENERATED 1
|
||||
)
|
||||
|
||||
endmacro()
|
||||
|
||||
#
|
||||
# Create Swig module
|
||||
#
|
||||
macro(SWIG_ADD_MODULE name language)
|
||||
SWIG_MODULE_INITIALIZE(${name} ${language})
|
||||
set(swig_dot_i_sources)
|
||||
set(swig_other_sources)
|
||||
foreach(it ${ARGN})
|
||||
if(${it} MATCHES ".*\\.i$")
|
||||
set(swig_dot_i_sources ${swig_dot_i_sources} "${it}")
|
||||
else()
|
||||
set(swig_other_sources ${swig_other_sources} "${it}")
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
set(swig_generated_sources)
|
||||
foreach(it ${swig_dot_i_sources})
|
||||
SWIG_ADD_SOURCE_TO_MODULE(${name} swig_generated_source ${it})
|
||||
set(swig_generated_sources ${swig_generated_sources} "${swig_generated_source}")
|
||||
endforeach()
|
||||
get_directory_property(swig_extra_clean_files ADDITIONAL_MAKE_CLEAN_FILES)
|
||||
set_directory_properties(PROPERTIES
|
||||
ADDITIONAL_MAKE_CLEAN_FILES "${swig_extra_clean_files};${swig_generated_sources}")
|
||||
add_library(${SWIG_MODULE_${name}_REAL_NAME}
|
||||
MODULE
|
||||
${swig_generated_sources}
|
||||
${swig_other_sources})
|
||||
string(TOLOWER "${language}" swig_lowercase_language)
|
||||
if ("${swig_lowercase_language}" STREQUAL "java")
|
||||
if (APPLE)
|
||||
# In java you want:
|
||||
# System.loadLibrary("LIBRARY");
|
||||
# then JNI will look for a library whose name is platform dependent, namely
|
||||
# MacOS : libLIBRARY.jnilib
|
||||
# Windows: LIBRARY.dll
|
||||
# Linux : libLIBRARY.so
|
||||
set_target_properties (${SWIG_MODULE_${name}_REAL_NAME} PROPERTIES SUFFIX ".jnilib")
|
||||
endif ()
|
||||
endif ()
|
||||
if ("${swig_lowercase_language}" STREQUAL "python")
|
||||
# this is only needed for the python case where a _modulename.so is generated
|
||||
set_target_properties(${SWIG_MODULE_${name}_REAL_NAME} PROPERTIES PREFIX "")
|
||||
# Python extension modules on Windows must have the extension ".pyd"
|
||||
# instead of ".dll" as of Python 2.5. Older python versions do support
|
||||
# this suffix.
|
||||
# http://docs.python.org/whatsnew/ports.html#SECTION0001510000000000000000
|
||||
# <quote>
|
||||
# Windows: .dll is no longer supported as a filename extension for extension modules.
|
||||
# .pyd is now the only filename extension that will be searched for.
|
||||
# </quote>
|
||||
if(WIN32 AND NOT CYGWIN)
|
||||
set_target_properties(${SWIG_MODULE_${name}_REAL_NAME} PROPERTIES SUFFIX ".pyd")
|
||||
endif()
|
||||
endif ()
|
||||
endmacro()
|
||||
|
||||
#
|
||||
# Like TARGET_LINK_LIBRARIES but for swig modules
|
||||
#
|
||||
macro(SWIG_LINK_LIBRARIES name)
|
||||
if(SWIG_MODULE_${name}_REAL_NAME)
|
||||
target_link_libraries(${SWIG_MODULE_${name}_REAL_NAME} ${ARGN})
|
||||
else()
|
||||
message(SEND_ERROR "Cannot find Swig library \"${name}\".")
|
||||
endif()
|
||||
endmacro()
|
|
@ -24,8 +24,6 @@ FIND_LIBRARY(
|
|||
/usr/lib64
|
||||
)
|
||||
|
||||
include("${CMAKE_CURRENT_LIST_DIR}/gnuradio-satnogsTargets.cmake")
|
||||
|
||||
INCLUDE(FindPackageHandleStandardArgs)
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS(SATNOGS DEFAULT_MSG SATNOGS_LIBRARIES SATNOGS_INCLUDE_DIRS)
|
||||
MARK_AS_ADVANCED(SATNOGS_LIBRARIES SATNOGS_INCLUDE_DIRS)
|
||||
|
|
|
@ -1,26 +0,0 @@
|
|||
# Copyright 2018 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio 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, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# GNU Radio 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 GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA 02110-1301, USA.
|
||||
|
||||
include(CMakeFindDependencyMacro)
|
||||
|
||||
set(target_deps "@TARGET_DEPENDENCIES@")
|
||||
foreach(dep IN LISTS target_deps)
|
||||
find_dependency(${dep})
|
||||
endforeach()
|
||||
include("${CMAKE_CURRENT_LIST_DIR}/@TARGET@Targets.cmake")
|
|
@ -1,5 +0,0 @@
|
|||
gr-satnogs (0.0-1) unstable; urgency=medium
|
||||
|
||||
* Update to upstream version v0.0
|
||||
|
||||
-- SatNOGS project <dev@satnogs.org> Tue, 12 Feb 2019 13:48:31 +0200
|
|
@ -1 +0,0 @@
|
|||
9
|
|
@ -1,57 +0,0 @@
|
|||
Source: gr-satnogs
|
||||
Section: science
|
||||
Priority: optional
|
||||
Maintainer: SatNOGS project <dev@satnogs.org>
|
||||
Build-Depends: cmake,
|
||||
debhelper (>= 9.0.0~),
|
||||
dh-python,
|
||||
doxygen,
|
||||
git,
|
||||
gnuradio-dev (>=3.8),
|
||||
gr-soapy,
|
||||
libboost-date-time-dev,
|
||||
libboost-dev,
|
||||
libboost-filesystem-dev,
|
||||
libboost-program-options-dev,
|
||||
libboost-regex-dev,
|
||||
libboost-system-dev,
|
||||
libboost-test-dev,
|
||||
libboost-thread-dev,
|
||||
libjsoncpp-dev,
|
||||
liborc-0.4-dev,
|
||||
libpng++-dev,
|
||||
libvorbis-dev,
|
||||
pkg-config,
|
||||
python3-dev,
|
||||
python3-six,
|
||||
swig
|
||||
Standards-Version: 4.1.0
|
||||
Homepage: https://gitlab.com/librespacefoundation/satnogs/gr-satnogs
|
||||
Vcs-Git: https://gitlab.com/librespacefoundation/satnogs/gr-satnogs.git
|
||||
Vcs-Browser: https://gitlab.com/librespacefoundation/satnogs/gr-satnogs
|
||||
|
||||
Package: gr-satnogs
|
||||
Architecture: any
|
||||
Pre-Depends: ${misc:Pre-Depends}
|
||||
Depends: libgnuradio-satnogs (= ${binary:Version}),
|
||||
python3,
|
||||
${python3:Depends},
|
||||
${shlibs:Depends},
|
||||
${misc:Depends}
|
||||
Recommends: gnuradio,
|
||||
gr-soapy
|
||||
Description: SatNOGS GNU Radio Out-Of-Tree Module
|
||||
gr-satnogs is an out-of-tree GNU Radio module that provides all the necessary
|
||||
tools for decoding signals from various scientific and academic sattelites.
|
||||
|
||||
Package: libgnuradio-satnogs
|
||||
Section: libs
|
||||
Architecture: any
|
||||
Pre-Depends: ${misc:Pre-Depends}
|
||||
Depends: ${misc:Depends}, ${shlibs:Depends}
|
||||
Multi-Arch: same
|
||||
Description: SatNOGS GNU Radio Out-Of-Tree Module
|
||||
gr-satnogs is an out-of-tree GNU Radio module that provides all the necessary
|
||||
tools for decoding signals from various scientific and academic sattelites.
|
||||
.
|
||||
This package contains the shared library.
|
|
@ -1,6 +0,0 @@
|
|||
usr/bin/*
|
||||
usr/include/*
|
||||
usr/lib/*/lib*.so
|
||||
usr/lib/*/cmake/*
|
||||
usr/lib/python*
|
||||
usr/share/*
|
|
@ -1 +0,0 @@
|
|||
usr/lib/*/lib*.so.*
|
|
@ -1,10 +0,0 @@
|
|||
Index: gr-satnogs/CMakeLists.txt
|
||||
===================================================================
|
||||
--- a/CMakeLists.txt
|
||||
+++ b/CMakeLists.txt
|
||||
@@ -46,4 +46,4 @@ list(INSERT CMAKE_MODULE_PATH 0 ${CMAKE_SOURCE_DIR}/cmake/Modules)
|
||||
-set(VERSION_PATCH git)
|
||||
+set(VERSION_PATCH 0)
|
||||
|
||||
cmake_policy(SET CMP0011 NEW)
|
||||
|
|
@ -1 +0,0 @@
|
|||
0001-remove-git-maint-version.patch
|
|
@ -1,27 +0,0 @@
|
|||
#!/usr/bin/make -f
|
||||
DEB_HOST_MULTIARCH ?= $(shell dpkg-architecture -qDEB_HOST_MULTIARCH)
|
||||
export DEB_HOST_MULTIARCH
|
||||
DEB_DEBIAN_DIR=$(dir $(firstword $(MAKEFILE_LIST)))
|
||||
VER=$(shell dpkg-parsechangelog -l$(DEB_DEBIAN_DIR)/changelog \
|
||||
| sed -rne 's,^Version: ([^-]+).*,\1,p')
|
||||
GITREV=$(shell echo $(VER) | sed -rne 's,^[0-9]+\.[0-9]+.*\+[0-9]+\+g([0-f]{8})$$,\1,p' -e 's,^([0-9]+\.[0-9]+(\.[0-9]+)?)$$,v\1,p')
|
||||
GITCOUNT=$(shell echo $(VER) | sed -rne 's,^[0-9]+\.[0-9]+.*\+([0-9]+)\+g[0-f]{8}$$,\1,p')
|
||||
|
||||
%:
|
||||
dh $@ --with python3 --parallel
|
||||
|
||||
override_dh_auto_configure:
|
||||
dh_auto_configure -- -DLIB_SUFFIX="/$(DEB_HOST_MULTIARCH)" -DGR_GIT_COUNT="$(GITCOUNT)" -DGR_GIT_HASH="$(GITREV)"
|
||||
|
||||
override_dh_auto_install:
|
||||
rm -f debian/gr-satnogs/usr/lib/python3/dist-packages/satnogs/*pyc
|
||||
rm -f debian/gr-satnogs/usr/lib/python3/dist-packages/satnogs/*pyo
|
||||
dh_auto_install
|
||||
|
||||
version-to-get:
|
||||
echo $(VER) is $(GITREV)
|
||||
|
||||
get-orig-source: version-to-get
|
||||
git clone https://gitlab.com/librespacefoundation/satnogs/gr-satnogs.git .gr-satnogs
|
||||
cd .gr-satnogs && git archive --format=tar --prefix=gr-satnogs-$(VER)/ $(GITREV) | xz > ../gr-satnogs_$(VER).orig.tar.xz
|
||||
rm -rf .gr-satnogs
|
|
@ -1 +0,0 @@
|
|||
3.0 (quilt)
|
Binary file not shown.
Before Width: | Height: | Size: 13 KiB |
Binary file not shown.
Before Width: | Height: | Size: 3.4 KiB |
Binary file not shown.
Before Width: | Height: | Size: 8.6 KiB |
|
@ -1,7 +1,6 @@
|
|||
# Copyright 2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-satnogs
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
|
|
@ -945,7 +945,7 @@ HTML_STYLESHEET =
|
|||
# user-defined cascading style sheet that is included after the standard
|
||||
# style sheets created by doxygen. Using this option one can overrule
|
||||
# certain style aspects. This is preferred over using HTML_STYLESHEET
|
||||
# since it does not replace the standard style sheet and is therefore more
|
||||
# since it does not replace the standard style sheet and is therefor more
|
||||
# robust against future updates. Doxygen will copy the style sheet file to
|
||||
# the output directory.
|
||||
|
||||
|
@ -989,7 +989,7 @@ HTML_COLORSTYLE_GAMMA = 80
|
|||
# page will contain the date and time when the page was generated. Setting
|
||||
# this to NO can help when comparing the output of multiple runs.
|
||||
|
||||
HTML_TIMESTAMP = NO
|
||||
HTML_TIMESTAMP = YES
|
||||
|
||||
# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML
|
||||
# documentation will contain sections that can be hidden and shown after the
|
||||
|
@ -1503,6 +1503,18 @@ GENERATE_XML = @enable_xml_docs@
|
|||
|
||||
XML_OUTPUT = xml
|
||||
|
||||
# The XML_SCHEMA tag can be used to specify an XML schema,
|
||||
# which can be used by a validating XML parser to check the
|
||||
# syntax of the XML files.
|
||||
|
||||
XML_SCHEMA =
|
||||
|
||||
# The XML_DTD tag can be used to specify an XML DTD,
|
||||
# which can be used by a validating XML parser to check the
|
||||
# syntax of the XML files.
|
||||
|
||||
XML_DTD =
|
||||
|
||||
# If the XML_PROGRAMLISTING tag is set to YES Doxygen will
|
||||
# dump the program listings (including syntax highlighting
|
||||
# and cross-referencing information) to the XML output. Note that
|
||||
|
|
|
@ -121,7 +121,7 @@ INLINE_INHERITED_MEMB = NO
|
|||
# path before files name in the file list and in the header files. If set
|
||||
# to NO the shortest path that makes the file name unique will be used.
|
||||
|
||||
FULL_PATH_NAMES = NO
|
||||
FULL_PATH_NAMES = YES
|
||||
|
||||
# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag
|
||||
# can be used to strip a user-defined part of the path. Stripping is
|
||||
|
@ -913,7 +913,7 @@ HTML_STYLESHEET =
|
|||
# user-defined cascading style sheet that is included after the standard
|
||||
# style sheets created by doxygen. Using this option one can overrule
|
||||
# certain style aspects. This is preferred over using HTML_STYLESHEET
|
||||
# since it does not replace the standard style sheet and is therefore more
|
||||
# since it does not replace the standard style sheet and is therefor more
|
||||
# robust against future updates. Doxygen will copy the style sheet file to
|
||||
# the output directory.
|
||||
|
||||
|
@ -957,7 +957,7 @@ HTML_COLORSTYLE_GAMMA = 80
|
|||
# page will contain the date and time when the page was generated. Setting
|
||||
# this to NO can help when comparing the output of multiple runs.
|
||||
|
||||
HTML_TIMESTAMP = NO
|
||||
HTML_TIMESTAMP = YES
|
||||
|
||||
# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML
|
||||
# documentation will contain sections that can be hidden and shown after the
|
||||
|
@ -1471,6 +1471,18 @@ GENERATE_XML = YES
|
|||
|
||||
XML_OUTPUT = xml
|
||||
|
||||
# The XML_SCHEMA tag can be used to specify an XML schema,
|
||||
# which can be used by a validating XML parser to check the
|
||||
# syntax of the XML files.
|
||||
|
||||
XML_SCHEMA =
|
||||
|
||||
# The XML_DTD tag can be used to specify an XML DTD,
|
||||
# which can be used by a validating XML parser to check the
|
||||
# syntax of the XML files.
|
||||
|
||||
XML_DTD =
|
||||
|
||||
# If the XML_PROGRAMLISTING tag is set to YES Doxygen will
|
||||
# dump the program listings (including syntax highlighting
|
||||
# and cross-referencing information) to the XML output. Note that
|
||||
|
|
|
@ -1,8 +1,7 @@
|
|||
#
|
||||
# Copyright 2010 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-satnogs
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
@ -64,9 +63,8 @@ This line is uninformative and is only to test line breaks in the comments.
|
|||
u'Outputs the vital aadvark statistics.'
|
||||
|
||||
"""
|
||||
from __future__ import unicode_literals
|
||||
|
||||
from .doxyindex import DoxyIndex, DoxyFunction, DoxyParam, DoxyClass, DoxyFile, DoxyNamespace, DoxyGroup, DoxyFriend, DoxyOther
|
||||
from doxyindex import DoxyIndex, DoxyFunction, DoxyParam, DoxyClass, DoxyFile, DoxyNamespace, DoxyGroup, DoxyFriend, DoxyOther
|
||||
|
||||
def _test():
|
||||
import os
|
||||
|
|
|
@ -1,8 +1,7 @@
|
|||
#
|
||||
# Copyright 2010 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-satnogs
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
@ -25,26 +24,24 @@ A base class is created.
|
|||
Classes based upon this are used to make more user-friendly interfaces
|
||||
to the doxygen xml docs than the generated classes provide.
|
||||
"""
|
||||
from __future__ import print_function
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import os
|
||||
import pdb
|
||||
|
||||
from xml.parsers.expat import ExpatError
|
||||
|
||||
from .generated import compound
|
||||
from generated import compound
|
||||
|
||||
|
||||
class Base(object):
|
||||
|
||||
class Duplicate(Exception):
|
||||
class Duplicate(StandardError):
|
||||
pass
|
||||
|
||||
class NoSuchMember(Exception):
|
||||
class NoSuchMember(StandardError):
|
||||
pass
|
||||
|
||||
class ParsingError(Exception):
|
||||
class ParsingError(StandardError):
|
||||
pass
|
||||
|
||||
def __init__(self, parse_data, top=None):
|
||||
|
@ -97,7 +94,7 @@ class Base(object):
|
|||
for cls in self.mem_classes:
|
||||
if cls.can_parse(mem):
|
||||
return cls
|
||||
raise Exception(("Did not find a class for object '%s'." \
|
||||
raise StandardError(("Did not find a class for object '%s'." \
|
||||
% (mem.get_name())))
|
||||
|
||||
def convert_mem(self, mem):
|
||||
|
@ -105,11 +102,11 @@ class Base(object):
|
|||
cls = self.get_cls(mem)
|
||||
converted = cls.from_parse_data(mem, self.top)
|
||||
if converted is None:
|
||||
raise Exception('No class matched this object.')
|
||||
raise StandardError('No class matched this object.')
|
||||
self.add_ref(converted)
|
||||
return converted
|
||||
except Exception as e:
|
||||
print(e)
|
||||
except StandardError, e:
|
||||
print e
|
||||
|
||||
@classmethod
|
||||
def includes(cls, inst):
|
||||
|
|
|
@ -1,8 +1,7 @@
|
|||
#
|
||||
# Copyright 2010 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-satnogs
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
@ -23,14 +22,12 @@
|
|||
Classes providing more user-friendly interfaces to the doxygen xml
|
||||
docs than the generated classes provide.
|
||||
"""
|
||||
from __future__ import absolute_import
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import os
|
||||
|
||||
from .generated import index
|
||||
from .base import Base
|
||||
from .text import description
|
||||
from generated import index
|
||||
from base import Base
|
||||
from text import description
|
||||
|
||||
class DoxyIndex(Base):
|
||||
"""
|
||||
|
@ -46,16 +43,13 @@ class DoxyIndex(Base):
|
|||
self._root = index.parse(os.path.join(self._xml_path, 'index.xml'))
|
||||
for mem in self._root.compound:
|
||||
converted = self.convert_mem(mem)
|
||||
# For files and namespaces we want the contents to be
|
||||
# accessible directly from the parent rather than having
|
||||
# to go through the file object.
|
||||
# For files we want the contents to be accessible directly
|
||||
# from the parent rather than having to go through the file
|
||||
# object.
|
||||
if self.get_cls(mem) == DoxyFile:
|
||||
if mem.name.endswith('.h'):
|
||||
self._members += converted.members()
|
||||
self._members.append(converted)
|
||||
elif self.get_cls(mem) == DoxyNamespace:
|
||||
self._members += converted.members()
|
||||
self._members.append(converted)
|
||||
else:
|
||||
self._members.append(converted)
|
||||
|
||||
|
@ -86,29 +80,13 @@ class DoxyCompMem(Base):
|
|||
self._data['brief_description'] = bd
|
||||
self._data['detailed_description'] = dd
|
||||
|
||||
def set_parameters(self, data):
|
||||
vs = [ddc.value for ddc in data.detaileddescription.content_]
|
||||
pls = []
|
||||
for v in vs:
|
||||
if hasattr(v, 'parameterlist'):
|
||||
pls += v.parameterlist
|
||||
pis = []
|
||||
for pl in pls:
|
||||
pis += pl.parameteritem
|
||||
dpis = []
|
||||
for pi in pis:
|
||||
dpi = DoxyParameterItem(pi)
|
||||
dpi._parse()
|
||||
dpis.append(dpi)
|
||||
self._data['params'] = dpis
|
||||
|
||||
|
||||
class DoxyCompound(DoxyCompMem):
|
||||
pass
|
||||
|
||||
class DoxyMember(DoxyCompMem):
|
||||
pass
|
||||
|
||||
|
||||
class DoxyFunction(DoxyMember):
|
||||
|
||||
__module__ = "gnuradio.utils.doxyxml"
|
||||
|
@ -120,13 +98,10 @@ class DoxyFunction(DoxyMember):
|
|||
return
|
||||
super(DoxyFunction, self)._parse()
|
||||
self.set_descriptions(self._parse_data)
|
||||
self.set_parameters(self._parse_data)
|
||||
if not self._data['params']:
|
||||
# If the params weren't set by a comment then just grab the names.
|
||||
self._data['params'] = []
|
||||
prms = self._parse_data.param
|
||||
for prm in prms:
|
||||
self._data['params'].append(DoxyParam(prm))
|
||||
self._data['params'] = []
|
||||
prms = self._parse_data.param
|
||||
for prm in prms:
|
||||
self._data['params'].append(DoxyParam(prm))
|
||||
|
||||
brief_description = property(lambda self: self.data()['brief_description'])
|
||||
detailed_description = property(lambda self: self.data()['detailed_description'])
|
||||
|
@ -146,39 +121,9 @@ class DoxyParam(DoxyMember):
|
|||
self.set_descriptions(self._parse_data)
|
||||
self._data['declname'] = self._parse_data.declname
|
||||
|
||||
@property
|
||||
def description(self):
|
||||
descriptions = []
|
||||
if self.brief_description:
|
||||
descriptions.append(self.brief_description)
|
||||
if self.detailed_description:
|
||||
descriptions.append(self.detailed_description)
|
||||
return '\n\n'.join(descriptions)
|
||||
|
||||
brief_description = property(lambda self: self.data()['brief_description'])
|
||||
detailed_description = property(lambda self: self.data()['detailed_description'])
|
||||
name = property(lambda self: self.data()['declname'])
|
||||
|
||||
class DoxyParameterItem(DoxyMember):
|
||||
"""A different representation of a parameter in Doxygen."""
|
||||
|
||||
def _parse(self):
|
||||
if self._parsed:
|
||||
return
|
||||
super(DoxyParameterItem, self)._parse()
|
||||
names = []
|
||||
for nl in self._parse_data.parameternamelist:
|
||||
for pn in nl.parametername:
|
||||
names.append(description(pn))
|
||||
# Just take first name
|
||||
self._data['name'] = names[0]
|
||||
# Get description
|
||||
pd = description(self._parse_data.get_parameterdescription())
|
||||
self._data['description'] = pd
|
||||
|
||||
description = property(lambda self: self.data()['description'])
|
||||
name = property(lambda self: self.data()['name'])
|
||||
|
||||
declname = property(lambda self: self.data()['declname'])
|
||||
|
||||
class DoxyClass(DoxyCompound):
|
||||
|
||||
|
@ -194,14 +139,12 @@ class DoxyClass(DoxyCompound):
|
|||
if self._error:
|
||||
return
|
||||
self.set_descriptions(self._retrieved_data.compounddef)
|
||||
self.set_parameters(self._retrieved_data.compounddef)
|
||||
# Sectiondef.kind tells about whether private or public.
|
||||
# We just ignore this for now.
|
||||
self.process_memberdefs()
|
||||
|
||||
brief_description = property(lambda self: self.data()['brief_description'])
|
||||
detailed_description = property(lambda self: self.data()['detailed_description'])
|
||||
params = property(lambda self: self.data()['params'])
|
||||
|
||||
Base.mem_classes.append(DoxyClass)
|
||||
|
||||
|
@ -234,16 +177,6 @@ class DoxyNamespace(DoxyCompound):
|
|||
|
||||
kind = 'namespace'
|
||||
|
||||
def _parse(self):
|
||||
if self._parsed:
|
||||
return
|
||||
super(DoxyNamespace, self)._parse()
|
||||
self.retrieve_data()
|
||||
self.set_descriptions(self._retrieved_data.compounddef)
|
||||
if self._error:
|
||||
return
|
||||
self.process_memberdefs()
|
||||
|
||||
Base.mem_classes.append(DoxyNamespace)
|
||||
|
||||
|
||||
|
@ -294,11 +227,11 @@ class DoxyOther(Base):
|
|||
|
||||
__module__ = "gnuradio.utils.doxyxml"
|
||||
|
||||
kinds = set(['variable', 'struct', 'union', 'define', 'typedef', 'enum',
|
||||
'dir', 'page', 'signal', 'slot', 'property'])
|
||||
kinds = set(['variable', 'struct', 'union', 'define', 'typedef', 'enum', 'dir', 'page'])
|
||||
|
||||
@classmethod
|
||||
def can_parse(cls, obj):
|
||||
return obj.kind in cls.kinds
|
||||
|
||||
Base.mem_classes.append(DoxyOther)
|
||||
|
||||
|
|
|
@ -5,4 +5,3 @@ These do the real work of parsing the doxygen xml files but the
|
|||
resultant classes are not very friendly to navigate so the rest of the
|
||||
doxyxml module processes them further.
|
||||
"""
|
||||
from __future__ import unicode_literals
|
||||
|
|
|
@ -3,17 +3,15 @@
|
|||
"""
|
||||
Generated Mon Feb 9 19:08:05 2009 by generateDS.py.
|
||||
"""
|
||||
from __future__ import absolute_import
|
||||
from __future__ import unicode_literals
|
||||
|
||||
|
||||
from string import lower as str_lower
|
||||
from xml.dom import minidom
|
||||
from xml.dom import Node
|
||||
|
||||
import sys
|
||||
|
||||
from . import compoundsuper as supermod
|
||||
from .compoundsuper import MixedContainer
|
||||
import compoundsuper as supermod
|
||||
from compoundsuper import MixedContainer
|
||||
|
||||
|
||||
class DoxygenTypeSub(supermod.DoxygenType):
|
||||
|
|
|
@ -4,17 +4,12 @@
|
|||
# Generated Thu Jun 11 18:44:25 2009 by generateDS.py.
|
||||
#
|
||||
|
||||
from __future__ import print_function
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import sys
|
||||
|
||||
import getopt
|
||||
from string import lower as str_lower
|
||||
from xml.dom import minidom
|
||||
from xml.dom import Node
|
||||
|
||||
import six
|
||||
|
||||
|
||||
#
|
||||
# User methods
|
||||
#
|
||||
|
@ -24,9 +19,9 @@ import six
|
|||
|
||||
try:
|
||||
from generatedssuper import GeneratedsSuper
|
||||
except ImportError as exp:
|
||||
except ImportError, exp:
|
||||
|
||||
class GeneratedsSuper(object):
|
||||
class GeneratedsSuper:
|
||||
def format_string(self, input_data, input_name=''):
|
||||
return input_data
|
||||
def format_integer(self, input_data, input_name=''):
|
||||
|
@ -69,7 +64,7 @@ def showIndent(outfile, level):
|
|||
outfile.write(' ')
|
||||
|
||||
def quote_xml(inStr):
|
||||
s1 = (isinstance(inStr, six.string_types) and inStr or
|
||||
s1 = (isinstance(inStr, basestring) and inStr or
|
||||
'%s' % inStr)
|
||||
s1 = s1.replace('&', '&')
|
||||
s1 = s1.replace('<', '<')
|
||||
|
@ -77,7 +72,7 @@ def quote_xml(inStr):
|
|||
return s1
|
||||
|
||||
def quote_attrib(inStr):
|
||||
s1 = (isinstance(inStr, six.string_types) and inStr or
|
||||
s1 = (isinstance(inStr, basestring) and inStr or
|
||||
'%s' % inStr)
|
||||
s1 = s1.replace('&', '&')
|
||||
s1 = s1.replace('<', '<')
|
||||
|
@ -107,7 +102,7 @@ def quote_python(inStr):
|
|||
return '"""%s"""' % s1
|
||||
|
||||
|
||||
class MixedContainer(object):
|
||||
class MixedContainer:
|
||||
# Constants for category:
|
||||
CategoryNone = 0
|
||||
CategoryText = 1
|
||||
|
@ -4226,7 +4221,7 @@ class codelineType(GeneratedsSuper):
|
|||
if attrs.get('lineno'):
|
||||
try:
|
||||
self.lineno = int(attrs.get('lineno').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (lineno): %s' % exp)
|
||||
if attrs.get('refkind'):
|
||||
self.refkind = attrs.get('refkind').value
|
||||
|
@ -4509,12 +4504,12 @@ class referenceType(GeneratedsSuper):
|
|||
if attrs.get('endline'):
|
||||
try:
|
||||
self.endline = int(attrs.get('endline').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (endline): %s' % exp)
|
||||
if attrs.get('startline'):
|
||||
try:
|
||||
self.startline = int(attrs.get('startline').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (startline): %s' % exp)
|
||||
if attrs.get('refid'):
|
||||
self.refid = attrs.get('refid').value
|
||||
|
@ -4632,17 +4627,17 @@ class locationType(GeneratedsSuper):
|
|||
if attrs.get('bodystart'):
|
||||
try:
|
||||
self.bodystart = int(attrs.get('bodystart').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (bodystart): %s' % exp)
|
||||
if attrs.get('line'):
|
||||
try:
|
||||
self.line = int(attrs.get('line').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (line): %s' % exp)
|
||||
if attrs.get('bodyend'):
|
||||
try:
|
||||
self.bodyend = int(attrs.get('bodyend').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (bodyend): %s' % exp)
|
||||
if attrs.get('bodyfile'):
|
||||
self.bodyfile = attrs.get('bodyfile').value
|
||||
|
@ -6783,12 +6778,12 @@ class docTableType(GeneratedsSuper):
|
|||
if attrs.get('rows'):
|
||||
try:
|
||||
self.rows = int(attrs.get('rows').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (rows): %s' % exp)
|
||||
if attrs.get('cols'):
|
||||
try:
|
||||
self.cols = int(attrs.get('cols').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (cols): %s' % exp)
|
||||
def buildChildren(self, child_, nodeName_):
|
||||
if child_.nodeType == Node.ELEMENT_NODE and \
|
||||
|
@ -7113,7 +7108,7 @@ class docHeadingType(GeneratedsSuper):
|
|||
if attrs.get('level'):
|
||||
try:
|
||||
self.level = int(attrs.get('level').value)
|
||||
except ValueError as exp:
|
||||
except ValueError, exp:
|
||||
raise ValueError('Bad integer attribute (level): %s' % exp)
|
||||
def buildChildren(self, child_, nodeName_):
|
||||
if child_.nodeType == Node.TEXT_NODE:
|
||||
|
@ -8288,7 +8283,7 @@ Options:
|
|||
"""
|
||||
|
||||
def usage():
|
||||
print(USAGE_TEXT)
|
||||
print USAGE_TEXT
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
|
@ -8344,3 +8339,4 @@ if __name__ == '__main__':
|
|||
main()
|
||||
#import pdb
|
||||
#pdb.run('main()')
|
||||
|
||||
|
|
|
@ -3,16 +3,14 @@
|
|||
"""
|
||||
Generated Mon Feb 9 19:08:05 2009 by generateDS.py.
|
||||
"""
|
||||
from __future__ import absolute_import
|
||||
from __future__ import unicode_literals
|
||||
|
||||
from xml.dom import minidom
|
||||
|
||||
import os
|
||||
import sys
|
||||
from . import compound
|
||||
import compound
|
||||
|
||||
from . import indexsuper as supermod
|
||||
import indexsuper as supermod
|
||||
|
||||
class DoxygenTypeSub(supermod.DoxygenType):
|
||||
def __init__(self, version=None, compound=None):
|
||||
|
|
|
@ -4,16 +4,12 @@
|
|||
# Generated Thu Jun 11 18:43:54 2009 by generateDS.py.
|
||||
#
|
||||
|
||||
from __future__ import print_function
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import sys
|
||||
|
||||
import getopt
|
||||
from string import lower as str_lower
|
||||
from xml.dom import minidom
|
||||
from xml.dom import Node
|
||||
|
||||
import six
|
||||
|
||||
#
|
||||
# User methods
|
||||
#
|
||||
|
@ -23,9 +19,9 @@ import six
|
|||
|
||||
try:
|
||||
from generatedssuper import GeneratedsSuper
|
||||
except ImportError as exp:
|
||||
except ImportError, exp:
|
||||
|
||||
class GeneratedsSuper(object):
|
||||
class GeneratedsSuper:
|
||||
def format_string(self, input_data, input_name=''):
|
||||
return input_data
|
||||
def format_integer(self, input_data, input_name=''):
|
||||
|
@ -68,7 +64,7 @@ def showIndent(outfile, level):
|
|||
outfile.write(' ')
|
||||
|
||||
def quote_xml(inStr):
|
||||
s1 = (isinstance(inStr, six.string_types) and inStr or
|
||||
s1 = (isinstance(inStr, basestring) and inStr or
|
||||
'%s' % inStr)
|
||||
s1 = s1.replace('&', '&')
|
||||
s1 = s1.replace('<', '<')
|
||||
|
@ -76,7 +72,7 @@ def quote_xml(inStr):
|
|||
return s1
|
||||
|
||||
def quote_attrib(inStr):
|
||||
s1 = (isinstance(inStr, six.string_types) and inStr or
|
||||
s1 = (isinstance(inStr, basestring) and inStr or
|
||||
'%s' % inStr)
|
||||
s1 = s1.replace('&', '&')
|
||||
s1 = s1.replace('<', '<')
|
||||
|
@ -106,7 +102,7 @@ def quote_python(inStr):
|
|||
return '"""%s"""' % s1
|
||||
|
||||
|
||||
class MixedContainer(object):
|
||||
class MixedContainer:
|
||||
# Constants for category:
|
||||
CategoryNone = 0
|
||||
CategoryText = 1
|
||||
|
@ -466,7 +462,7 @@ Options:
|
|||
"""
|
||||
|
||||
def usage():
|
||||
print(USAGE_TEXT)
|
||||
print USAGE_TEXT
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
|
@ -524,3 +520,4 @@ if __name__ == '__main__':
|
|||
main()
|
||||
#import pdb
|
||||
#pdb.run('main()')
|
||||
|
||||
|
|
|
@ -1,8 +1,7 @@
|
|||
#
|
||||
# Copyright 2010 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-satnogs
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
@ -22,13 +21,12 @@
|
|||
"""
|
||||
Utilities for extracting text from generated classes.
|
||||
"""
|
||||
from __future__ import unicode_literals
|
||||
|
||||
def is_string(txt):
|
||||
if isinstance(txt, str):
|
||||
return True
|
||||
try:
|
||||
if isinstance(txt, str):
|
||||
if isinstance(txt, unicode):
|
||||
return True
|
||||
except NameError:
|
||||
pass
|
||||
|
@ -51,7 +49,7 @@ def description_bit(obj):
|
|||
elif is_string(obj):
|
||||
return obj
|
||||
else:
|
||||
raise Exception('Expecting a string or something with content, content_ or value attribute')
|
||||
raise StandardError('Expecting a string or something with content, content_ or value attribute')
|
||||
# If this bit is a paragraph then add one some line breaks.
|
||||
if hasattr(obj, 'name') and obj.name == 'para':
|
||||
result += "\n\n"
|
||||
|
|
|
@ -1,8 +1,7 @@
|
|||
#
|
||||
# Copyright 2010-2012 Free Software Foundation, Inc.
|
||||
# Copyright 2010,2011 Free Software Foundation, Inc.
|
||||
#
|
||||
# This file was generated by gr_modtool, a tool from the GNU Radio framework
|
||||
# This file is a part of gr-inspector
|
||||
# This file is part of GNU Radio
|
||||
#
|
||||
# GNU Radio is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
|
@ -22,15 +21,19 @@
|
|||
"""
|
||||
Creates the swig_doc.i SWIG interface file.
|
||||
Execute using: python swig_doc.py xml_path outputfilename
|
||||
|
||||
The file instructs SWIG to transfer the doxygen comments into the
|
||||
python docstrings.
|
||||
|
||||
"""
|
||||
from __future__ import unicode_literals
|
||||
|
||||
import sys, time
|
||||
import sys
|
||||
|
||||
try:
|
||||
from doxyxml import DoxyIndex, DoxyClass, DoxyFriend, DoxyFunction, DoxyFile, base
|
||||
except ImportError:
|
||||
from gnuradio.doxyxml import DoxyIndex, DoxyClass, DoxyFriend, DoxyFunction, DoxyFile, base
|
||||
|
||||
from doxyxml import DoxyIndex, DoxyClass, DoxyFriend, DoxyFunction, DoxyFile
|
||||
from doxyxml import DoxyOther, base
|
||||
|
||||
def py_name(name):
|
||||
bits = name.split('_')
|
||||
|
@ -53,41 +56,18 @@ class Block(object):
|
|||
# Check for a parsing error.
|
||||
if item.error():
|
||||
return False
|
||||
friendname = make_name(item.name())
|
||||
is_a_block = item.has_member(friendname, DoxyFriend)
|
||||
# But now sometimes the make function isn't a friend so check again.
|
||||
if not is_a_block:
|
||||
is_a_block = di.has_member(friendname, DoxyFunction)
|
||||
return is_a_block
|
||||
|
||||
class Block2(object):
|
||||
"""
|
||||
Checks if doxyxml produced objects correspond to a new style
|
||||
gnuradio block.
|
||||
"""
|
||||
|
||||
@classmethod
|
||||
def includes(cls, item):
|
||||
if not isinstance(item, DoxyClass):
|
||||
return False
|
||||
# Check for a parsing error.
|
||||
if item.error():
|
||||
return False
|
||||
is_a_block2 = item.has_member('make', DoxyFunction) and item.has_member('sptr', DoxyOther)
|
||||
return is_a_block2
|
||||
return item.has_member(make_name(item.name()), DoxyFriend)
|
||||
|
||||
|
||||
def utoascii(text):
|
||||
"""
|
||||
Convert unicode text into ascii and escape quotes and backslashes.
|
||||
Convert unicode text into ascii and escape quotes.
|
||||
"""
|
||||
if text is None:
|
||||
return ''
|
||||
out = text.encode('ascii', 'replace')
|
||||
# swig will require us to replace blackslash with 4 backslashes
|
||||
out = out.replace(b'\\', b'\\\\\\\\')
|
||||
out = out.replace(b'"', b'\\"').decode('ascii')
|
||||
return str(out)
|
||||
out = out.replace('"', '\\"')
|
||||
return out
|
||||
|
||||
|
||||
def combine_descriptions(obj):
|
||||
|
@ -103,17 +83,12 @@ def combine_descriptions(obj):
|
|||
description.append(dd)
|
||||
return utoascii('\n\n'.join(description)).strip()
|
||||
|
||||
def format_params(parameteritems):
|
||||
output = ['Args:']
|
||||
template = ' {0} : {1}'
|
||||
for pi in parameteritems:
|
||||
output.append(template.format(pi.name, pi.description))
|
||||
return '\n'.join(output)
|
||||
|
||||
entry_templ = '%feature("docstring") {name} "{docstring}"'
|
||||
def make_entry(obj, name=None, templ="{description}", description=None, params=[]):
|
||||
def make_entry(obj, name=None, templ="{description}", description=None):
|
||||
"""
|
||||
Create a docstring entry for a swig interface file.
|
||||
|
||||
obj - a doxyxml object from which documentation will be extracted.
|
||||
name - the name of the C object (defaults to obj.name())
|
||||
templ - an optional template for the docstring containing only one
|
||||
|
@ -127,9 +102,6 @@ def make_entry(obj, name=None, templ="{description}", description=None, params=[
|
|||
return ''
|
||||
if description is None:
|
||||
description = combine_descriptions(obj)
|
||||
if params:
|
||||
description += '\n\n'
|
||||
description += utoascii(format_params(params))
|
||||
docstring = templ.format(description=description)
|
||||
if not docstring:
|
||||
return ''
|
||||
|
@ -142,37 +114,34 @@ def make_entry(obj, name=None, templ="{description}", description=None, params=[
|
|||
def make_func_entry(func, name=None, description=None, params=None):
|
||||
"""
|
||||
Create a function docstring entry for a swig interface file.
|
||||
|
||||
func - a doxyxml object from which documentation will be extracted.
|
||||
name - the name of the C object (defaults to func.name())
|
||||
description - if this optional variable is set then it's value is
|
||||
used as the description instead of extracting it from func.
|
||||
params - a parameter list that overrides using func.params.
|
||||
"""
|
||||
#if params is None:
|
||||
# params = func.params
|
||||
#params = [prm.declname for prm in params]
|
||||
#if params:
|
||||
# sig = "Params: (%s)" % ", ".join(params)
|
||||
#else:
|
||||
# sig = "Params: (NONE)"
|
||||
#templ = "{description}\n\n" + sig
|
||||
#return make_entry(func, name=name, templ=utoascii(templ),
|
||||
# description=description)
|
||||
return make_entry(func, name=name, description=description, params=params)
|
||||
if params is None:
|
||||
params = func.params
|
||||
params = [prm.declname for prm in params]
|
||||
if params:
|
||||
sig = "Params: (%s)" % ", ".join(params)
|
||||
else:
|
||||
sig = "Params: (NONE)"
|
||||
templ = "{description}\n\n" + sig
|
||||
return make_entry(func, name=name, templ=utoascii(templ),
|
||||
description=description)
|
||||
|
||||
|
||||
def make_class_entry(klass, description=None, ignored_methods=[], params=None):
|
||||
def make_class_entry(klass, description=None):
|
||||
"""
|
||||
Create a class docstring for a swig interface file.
|
||||
"""
|
||||
if params is None:
|
||||
params = klass.params
|
||||
output = []
|
||||
output.append(make_entry(klass, description=description, params=params))
|
||||
output.append(make_entry(klass, description=description))
|
||||
for func in klass.in_category(DoxyFunction):
|
||||
if func.name() not in ignored_methods:
|
||||
name = klass.name() + '::' + func.name()
|
||||
output.append(make_func_entry(func, name=name))
|
||||
name = klass.name() + '::' + func.name()
|
||||
output.append(make_func_entry(func, name=name))
|
||||
return "\n\n".join(output)
|
||||
|
||||
|
||||
|
@ -206,33 +175,11 @@ def make_block_entry(di, block):
|
|||
# the make function.
|
||||
output = []
|
||||
output.append(make_class_entry(block, description=super_description))
|
||||
creator = block.get_member(block.name(), DoxyFunction)
|
||||
output.append(make_func_entry(make_func, description=super_description,
|
||||
params=block.params))
|
||||
params=creator.params))
|
||||
return "\n\n".join(output)
|
||||
|
||||
def make_block2_entry(di, block):
|
||||
"""
|
||||
Create class and function docstrings of a new style gnuradio block for a
|
||||
swig interface file.
|
||||
"""
|
||||
descriptions = []
|
||||
# For new style blocks all the relevant documentation should be
|
||||
# associated with the 'make' method.
|
||||
class_description = combine_descriptions(block)
|
||||
make_func = block.get_member('make', DoxyFunction)
|
||||
make_description = combine_descriptions(make_func)
|
||||
description = class_description + "\n\nConstructor Specific Documentation:\n\n" + make_description
|
||||
# Associate the combined description with the class and
|
||||
# the make function.
|
||||
output = []
|
||||
output.append(make_class_entry(
|
||||
block, description=description,
|
||||
ignored_methods=['make'], params=make_func.params))
|
||||
makename = block.name() + '::make'
|
||||
output.append(make_func_entry(
|
||||
make_func, name=makename, description=description,
|
||||
params=make_func.params))
|
||||
return "\n\n".join(output)
|
||||
|
||||
def make_swig_interface_file(di, swigdocfilename, custom_output=None):
|
||||
|
||||
|
@ -249,59 +196,39 @@ def make_swig_interface_file(di, swigdocfilename, custom_output=None):
|
|||
|
||||
# Create docstrings for the blocks.
|
||||
blocks = di.in_category(Block)
|
||||
blocks2 = di.in_category(Block2)
|
||||
|
||||
make_funcs = set([])
|
||||
for block in blocks:
|
||||
try:
|
||||
make_func = di.get_member(make_name(block.name()), DoxyFunction)
|
||||
# Don't want to risk writing to output twice.
|
||||
if make_func.name() not in make_funcs:
|
||||
make_funcs.add(make_func.name())
|
||||
output.append(make_block_entry(di, block))
|
||||
make_funcs.add(make_func.name())
|
||||
output.append(make_block_entry(di, block))
|
||||
except block.ParsingError:
|
||||
sys.stderr.write('Parsing error for block {0}\n'.format(block.name()))
|
||||
raise
|
||||
|
||||
for block in blocks2:
|
||||
try:
|
||||
make_func = block.get_member('make', DoxyFunction)
|
||||
make_func_name = block.name() +'::make'
|
||||
# Don't want to risk writing to output twice.
|
||||
if make_func_name not in make_funcs:
|
||||
make_funcs.add(make_func_name)
|
||||
output.append(make_block2_entry(di, block))
|
||||
except block.ParsingError:
|
||||
sys.stderr.write('Parsing error for block {0}\n'.format(block.name()))
|
||||
raise
|
||||
print('Parsing error for block %s' % block.name())
|
||||
|
||||
# Create docstrings for functions
|
||||
# Don't include the make functions since they have already been dealt with.
|
||||
funcs = [f for f in di.in_category(DoxyFunction)
|
||||
if f.name() not in make_funcs and not f.name().startswith('std::')]
|
||||
funcs = [f for f in di.in_category(DoxyFunction) if f.name() not in make_funcs]
|
||||
for f in funcs:
|
||||
try:
|
||||
output.append(make_func_entry(f))
|
||||
except f.ParsingError:
|
||||
sys.stderr.write('Parsing error for function {0}\n'.format(f.name()))
|
||||
print('Parsing error for function %s' % f.name())
|
||||
|
||||
# Create docstrings for classes
|
||||
block_names = [block.name() for block in blocks]
|
||||
block_names += [block.name() for block in blocks2]
|
||||
klasses = [k for k in di.in_category(DoxyClass)
|
||||
if k.name() not in block_names and not k.name().startswith('std::')]
|
||||
klasses = [k for k in di.in_category(DoxyClass) if k.name() not in block_names]
|
||||
for k in klasses:
|
||||
try:
|
||||
output.append(make_class_entry(k))
|
||||
except k.ParsingError:
|
||||
sys.stderr.write('Parsing error for class {0}\n'.format(k.name()))
|
||||
print('Parsing error for class %s' % k.name())
|
||||
|
||||
# Docstrings are not created for anything that is not a function or a class.
|
||||
# If this excludes anything important please add it here.
|
||||
|
||||
output = "\n\n".join(output)
|
||||
|
||||
swig_doc = open(swigdocfilename, 'w')
|
||||
swig_doc = file(swigdocfilename, 'w')
|
||||
swig_doc.write(output)
|
||||
swig_doc.close()
|
||||
|
||||
|
@ -309,7 +236,7 @@ if __name__ == "__main__":
|
|||
# Parse command line options and set up doxyxml.
|
||||
err_msg = "Execute using: python swig_doc.py xml_path outputfilename"
|
||||
if len(sys.argv) != 3:
|
||||
raise Exception(err_msg)
|
||||
raise StandardError(err_msg)
|
||||
xml_path = sys.argv[1]
|
||||
swigdocfilename = sys.argv[2]
|
||||
di = DoxyIndex(xml_path)
|
||||
|
@ -325,4 +252,4 @@ if __name__ == "__main__":
|
|||
custom_output = "\n\n".join(output)
|
||||
|
||||
# Generate the docstrings interface file.
|
||||
make_swig_interface_file(di, swigdocfilename, custom_output=custom_output)
|
||||
make_swig_interface_file(di, swigdocfilename, custom_output=custom_output)
|
||||
|
|
Binary file not shown.
File diff suppressed because it is too large
Load Diff
|
@ -1,5 +1,5 @@
|
|||
<?xml version='1.0' encoding='utf-8'?>
|
||||
<?grc format='1' created='3.7.11'?>
|
||||
<?grc format='1' created='3.7.9'?>
|
||||
<flow_graph>
|
||||
<timestamp>Fri Mar 18 13:57:31 2016</timestamp>
|
||||
<block>
|
||||
|
@ -2284,7 +2284,7 @@ is too great and becomes a bottlneck.</value>
|
|||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(542, 754)</value>
|
||||
<value>(544, 689)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
|
@ -3859,10 +3859,6 @@ is too great and becomes a bottlneck.</value>
|
|||
<key>average</key>
|
||||
<value>1.0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>axislabels</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>bw</key>
|
||||
<value>samp_rate_rx/10.0</value>
|
||||
|
@ -4131,10 +4127,6 @@ is too great and becomes a bottlneck.</value>
|
|||
<key>wintype</key>
|
||||
<value>firdes.WIN_BLACKMAN_hARRIS</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>label</key>
|
||||
<value>Relative Gain</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ymax</key>
|
||||
<value>10</value>
|
||||
|
@ -4143,17 +4135,9 @@ is too great and becomes a bottlneck.</value>
|
|||
<key>ymin</key>
|
||||
<value>-140</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>units</key>
|
||||
<value>dB</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>qtgui_waterfall_sink_x</key>
|
||||
<param>
|
||||
<key>axislabels</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>bw</key>
|
||||
<value>samp_rate_rx/10.0</value>
|
||||
|
@ -4371,6 +4355,37 @@ is too great and becomes a bottlneck.</value>
|
|||
<value>firdes.WIN_BLACKMAN_hARRIS</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_clear_text_msg_sink</key>
|
||||
<param>
|
||||
<key>alias</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>1</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(288, 336)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>180</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>satnogs_clear_text_msg_sink_0</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_debug_msg_source</key>
|
||||
<param>
|
||||
|
@ -4422,53 +4437,6 @@ is too great and becomes a bottlneck.</value>
|
|||
<value>True</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_multi_format_msg_sink</key>
|
||||
<param>
|
||||
<key>alias</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>filename</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(247, 363)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>180</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>satnogs_multi_format_msg_sink_0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>outstream</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>timestamp</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>format</key>
|
||||
<value>1</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_udp_msg_source</key>
|
||||
<param>
|
||||
|
@ -4513,10 +4481,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>maxoutbuf</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>msg_type</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>minoutbuf</key>
|
||||
<value>0</value>
|
||||
|
@ -4572,34 +4536,14 @@ similar to produce dynamic payloads.</value>
|
|||
<key>minoutbuf</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>packet_len</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>sync_word</key>
|
||||
<value>[0x7A, 0x0E]</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ax_25</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>manchester</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening_mask</key>
|
||||
<value>0x1001</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening_order</key>
|
||||
<value>17</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening_seed</key>
|
||||
<value>0x1FF</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening</key>
|
||||
<value>True</value>
|
||||
|
@ -4623,14 +4567,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>dest_addr</key>
|
||||
<value>GND</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>dest_ssid</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>1</value>
|
||||
|
@ -4641,7 +4577,7 @@ similar to produce dynamic payloads.</value>
|
|||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(534, 506)</value>
|
||||
<value>(544, 482)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
|
@ -4667,22 +4603,10 @@ similar to produce dynamic payloads.</value>
|
|||
<key>msb_first</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>src_addr</key>
|
||||
<value>UPSAT</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>src_ssid</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>sync_word</key>
|
||||
<value>[0x7A, 0x0E]</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ax_25</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>manchester</key>
|
||||
<value>False</value>
|
||||
|
@ -4772,7 +4696,7 @@ similar to produce dynamic payloads.</value>
|
|||
</connection>
|
||||
<connection>
|
||||
<source_block_id>satnogs_upsat_fsk_frame_acquisition_0</source_block_id>
|
||||
<sink_block_id>satnogs_multi_format_msg_sink_0</sink_block_id>
|
||||
<sink_block_id>satnogs_clear_text_msg_sink_0</sink_block_id>
|
||||
<source_key>pdu</source_key>
|
||||
<sink_key>in</sink_key>
|
||||
</connection>
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
<?xml version='1.0' encoding='utf-8'?>
|
||||
<?grc format='1' created='3.7.11'?>
|
||||
<?grc format='1' created='3.7.9'?>
|
||||
<flow_graph>
|
||||
<timestamp>Fri Mar 18 13:57:31 2016</timestamp>
|
||||
<block>
|
||||
|
@ -1185,10 +1185,6 @@ is too great and becomes a bottlneck.</value>
|
|||
<key>average</key>
|
||||
<value>1.0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>axislabels</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>bw</key>
|
||||
<value>samp_rate_rx/10.0</value>
|
||||
|
@ -1457,10 +1453,6 @@ is too great and becomes a bottlneck.</value>
|
|||
<key>wintype</key>
|
||||
<value>firdes.WIN_BLACKMAN_hARRIS</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>label</key>
|
||||
<value>Relative Gain</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ymax</key>
|
||||
<value>10</value>
|
||||
|
@ -1469,17 +1461,9 @@ is too great and becomes a bottlneck.</value>
|
|||
<key>ymin</key>
|
||||
<value>-140</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>units</key>
|
||||
<value>dB</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>qtgui_waterfall_sink_x</key>
|
||||
<param>
|
||||
<key>axislabels</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>bw</key>
|
||||
<value>samp_rate_rx/10.0</value>
|
||||
|
@ -1697,6 +1681,37 @@ is too great and becomes a bottlneck.</value>
|
|||
<value>firdes.WIN_BLACKMAN_hARRIS</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_clear_text_msg_sink</key>
|
||||
<param>
|
||||
<key>alias</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>1</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(288, 336)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>180</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>satnogs_clear_text_msg_sink_0</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_debug_msg_source</key>
|
||||
<param>
|
||||
|
@ -1748,53 +1763,6 @@ is too great and becomes a bottlneck.</value>
|
|||
<value>True</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_multi_format_msg_sink</key>
|
||||
<param>
|
||||
<key>alias</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>filename</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(223, 331)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>180</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>satnogs_multi_format_msg_sink_0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>outstream</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>timestamp</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>format</key>
|
||||
<value>1</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_udp_msg_source</key>
|
||||
<param>
|
||||
|
@ -1817,7 +1785,7 @@ similar to produce dynamic payloads.</value>
|
|||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(223, 594)</value>
|
||||
<value>(216, 590)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
|
@ -1839,10 +1807,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>maxoutbuf</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>msg_type</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>minoutbuf</key>
|
||||
<value>0</value>
|
||||
|
@ -1880,7 +1844,7 @@ similar to produce dynamic payloads.</value>
|
|||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(534, 275)</value>
|
||||
<value>(536, 304)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
|
@ -1898,34 +1862,14 @@ similar to produce dynamic payloads.</value>
|
|||
<key>minoutbuf</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>packet_len</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>sync_word</key>
|
||||
<value>[0x7A, 0x0E]</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ax_25</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>manchester</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening_mask</key>
|
||||
<value>0x1001</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening_order</key>
|
||||
<value>17</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening_seed</key>
|
||||
<value>0x1FF</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>whitening</key>
|
||||
<value>True</value>
|
||||
|
@ -1949,14 +1893,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>dest_addr</key>
|
||||
<value>GND</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>dest_ssid</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>1</value>
|
||||
|
@ -1993,22 +1929,10 @@ similar to produce dynamic payloads.</value>
|
|||
<key>msb_first</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>src_addr</key>
|
||||
<value>UPSAT</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>src_ssid</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>sync_word</key>
|
||||
<value>[0x7A, 0x0E]</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ax_25</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>manchester</key>
|
||||
<value>False</value>
|
||||
|
@ -2816,10 +2740,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>hide_cmd_port</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>hide_lo_controls</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>stream_args</key>
|
||||
<value></value>
|
||||
|
@ -2875,14 +2795,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain0</key>
|
||||
<value>gain</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export0</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source0</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant10</key>
|
||||
<value></value>
|
||||
|
@ -2911,14 +2823,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain10</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export10</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source10</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant11</key>
|
||||
<value></value>
|
||||
|
@ -2947,14 +2851,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain11</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export11</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source11</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant12</key>
|
||||
<value></value>
|
||||
|
@ -2983,14 +2879,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain12</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export12</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source12</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant13</key>
|
||||
<value></value>
|
||||
|
@ -3019,14 +2907,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain13</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export13</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source13</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant14</key>
|
||||
<value></value>
|
||||
|
@ -3055,14 +2935,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain14</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export14</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source14</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant15</key>
|
||||
<value></value>
|
||||
|
@ -3091,14 +2963,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain15</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export15</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source15</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant16</key>
|
||||
<value></value>
|
||||
|
@ -3127,14 +2991,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain16</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export16</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source16</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant17</key>
|
||||
<value></value>
|
||||
|
@ -3163,14 +3019,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain17</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export17</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source17</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant18</key>
|
||||
<value></value>
|
||||
|
@ -3199,14 +3047,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain18</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export18</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source18</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant19</key>
|
||||
<value></value>
|
||||
|
@ -3235,14 +3075,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain19</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export19</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source19</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant1</key>
|
||||
<value></value>
|
||||
|
@ -3271,14 +3103,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain1</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export1</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source1</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant20</key>
|
||||
<value></value>
|
||||
|
@ -3307,14 +3131,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain20</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export20</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source20</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant21</key>
|
||||
<value></value>
|
||||
|
@ -3343,14 +3159,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain21</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export21</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source21</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant22</key>
|
||||
<value></value>
|
||||
|
@ -3379,14 +3187,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain22</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export22</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source22</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant23</key>
|
||||
<value></value>
|
||||
|
@ -3415,14 +3215,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain23</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export23</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source23</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant24</key>
|
||||
<value></value>
|
||||
|
@ -3451,14 +3243,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain24</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export24</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source24</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant25</key>
|
||||
<value></value>
|
||||
|
@ -3487,14 +3271,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain25</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export25</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source25</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant26</key>
|
||||
<value></value>
|
||||
|
@ -3523,14 +3299,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain26</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export26</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source26</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant27</key>
|
||||
<value></value>
|
||||
|
@ -3559,14 +3327,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain27</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export27</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source27</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant28</key>
|
||||
<value></value>
|
||||
|
@ -3595,14 +3355,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain28</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export28</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source28</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant29</key>
|
||||
<value></value>
|
||||
|
@ -3631,14 +3383,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain29</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export29</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source29</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant2</key>
|
||||
<value></value>
|
||||
|
@ -3667,14 +3411,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain2</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export2</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source2</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant30</key>
|
||||
<value></value>
|
||||
|
@ -3703,14 +3439,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain30</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export30</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source30</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant31</key>
|
||||
<value></value>
|
||||
|
@ -3739,14 +3467,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain31</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export31</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source31</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant3</key>
|
||||
<value></value>
|
||||
|
@ -3775,14 +3495,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain3</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export3</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source3</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant4</key>
|
||||
<value></value>
|
||||
|
@ -3811,14 +3523,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain4</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export4</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source4</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant5</key>
|
||||
<value></value>
|
||||
|
@ -3847,14 +3551,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain5</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export5</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source5</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant6</key>
|
||||
<value></value>
|
||||
|
@ -3883,14 +3579,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain6</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export6</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source6</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant7</key>
|
||||
<value></value>
|
||||
|
@ -3919,14 +3607,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain7</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export7</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source7</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant8</key>
|
||||
<value></value>
|
||||
|
@ -3955,14 +3635,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain8</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export8</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source8</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>ant9</key>
|
||||
<value></value>
|
||||
|
@ -3991,14 +3663,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>gain9</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_export9</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>lo_source9</key>
|
||||
<value>internal</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>clock_rate</key>
|
||||
<value>0.0</value>
|
||||
|
@ -4159,10 +3823,6 @@ similar to produce dynamic payloads.</value>
|
|||
<key>hide_cmd_port</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>hide_lo_controls</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>stream_args</key>
|
||||
<value></value>
|
||||
|
@ -4254,7 +3914,7 @@ similar to produce dynamic payloads.</value>
|
|||
</connection>
|
||||
<connection>
|
||||
<source_block_id>satnogs_upsat_fsk_frame_acquisition_0</source_block_id>
|
||||
<sink_block_id>satnogs_multi_format_msg_sink_0</sink_block_id>
|
||||
<sink_block_id>satnogs_clear_text_msg_sink_0</sink_block_id>
|
||||
<source_key>pdu</source_key>
|
||||
<sink_key>in</sink_key>
|
||||
</connection>
|
||||
|
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Binary file not shown.
File diff suppressed because it is too large
Load Diff
|
@ -1,5 +1,5 @@
|
|||
<?xml version='1.0' encoding='utf-8'?>
|
||||
<?grc format='1' created='3.7.11'?>
|
||||
<?grc format='1' created='3.7.10'?>
|
||||
<flow_graph>
|
||||
<timestamp>Fri Jan 22 20:01:21 2016</timestamp>
|
||||
<block>
|
||||
|
@ -78,7 +78,65 @@
|
|||
</param>
|
||||
<param>
|
||||
<key>title</key>
|
||||
<value>Morse Decoder Simple Example</value>
|
||||
<value></value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>variable</key>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(8, 160)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>samp_rate</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>value</key>
|
||||
<value>32000</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_clear_text_msg_sink</key>
|
||||
<param>
|
||||
<key>alias</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(960, 168)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>satnogs_clear_text_msg_sink_0</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
|
@ -129,15 +187,7 @@
|
|||
</param>
|
||||
<param>
|
||||
<key>debug_seq</key>
|
||||
<value>"SATNOGS HELLO EARTH WORLD 123456789"</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>seq_pause_ms</key>
|
||||
<value>1000</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>wpm</key>
|
||||
<value>20</value>
|
||||
<value>"XPGOLIAT HELLO EARTH WORLD 123456789"</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
|
@ -178,62 +228,11 @@
|
|||
<key>minoutbuf</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>min_frame_len</key>
|
||||
<value>3</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>unrecognized_char</key>
|
||||
<value>ord('#')</value>
|
||||
</param>
|
||||
</block>
|
||||
<block>
|
||||
<key>satnogs_multi_format_msg_sink</key>
|
||||
<param>
|
||||
<key>alias</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>comment</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>affinity</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_enabled</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>filename</key>
|
||||
<value></value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_coordinate</key>
|
||||
<value>(968, 148)</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>_rotation</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>id</key>
|
||||
<value>satnogs_multi_format_msg_sink_0</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>outstream</key>
|
||||
<value>True</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>timestamp</key>
|
||||
<value>False</value>
|
||||
</param>
|
||||
<param>
|
||||
<key>format</key>
|
||||
<value>0</value>
|
||||
</param>
|
||||
</block>
|
||||
<connection>
|
||||
<source_block_id>satnogs_morse_debug_source_0</source_block_id>
|
||||
<sink_block_id>satnogs_morse_decoder_0</sink_block_id>
|
||||
|
@ -242,7 +241,7 @@
|
|||
</connection>
|
||||
<connection>
|
||||
<source_block_id>satnogs_morse_decoder_0</source_block_id>
|
||||
<sink_block_id>satnogs_multi_format_msg_sink_0</sink_block_id>
|
||||
<sink_block_id>satnogs_clear_text_msg_sink_0</sink_block_id>
|
||||
<source_key>out</source_key>
|
||||
<sink_key>in</sink_key>
|
||||
</connection>
|
||||
|
|
|
@ -15,50 +15,28 @@
|
|||
# You should have received a copy of the GNU General Public License
|
||||
# along with GNU Radio; see the file COPYING. If not, write to
|
||||
# the Free Software Foundation, Inc., 51 Franklin Street,
|
||||
# Boston, MA
|
||||
|
||||
list(APPEND debug_blocks
|
||||
satnogs_cw_encoder.block.yml
|
||||
satnogs_cw_to_symbol.block.yml
|
||||
satnogs_debug_msg_source_raw.block.yml
|
||||
satnogs_debug_msg_source.block.yml
|
||||
satnogs_morse_debug_source.block.yml
|
||||
)
|
||||
|
||||
list(APPEND enabled_blocks
|
||||
satnogs_amsat_duv_decoder.block.yml
|
||||
satnogs_ax25_decoder.block.yml
|
||||
satnogs_ax25_encoder_mb.block.yml
|
||||
satnogs_ax100_decoder.block.yml
|
||||
satnogs_coarse_doppler_correction_cc.block.yml
|
||||
satnogs_doppler_compensation.block.yml
|
||||
satnogs_doppler_correction_cc.block.yml
|
||||
satnogs_frame_decoder.block.yml
|
||||
satnogs_frame_file_sink.block.yml
|
||||
satnogs_ieee802_15_4_variant_decoder.block.yml
|
||||
satnogs_iq_sink.block.yml
|
||||
satnogs_json_converter.block.yml
|
||||
satnogs_lrpt_decoder.block.yml
|
||||
satnogs_lrpt_sync.block.yml
|
||||
satnogs_morse_decoder.block.yml
|
||||
satnogs_multi_format_msg_sink.block.yml
|
||||
satnogs_noaa_apt_sink.block.yml
|
||||
satnogs_ogg_encoder.block.yml
|
||||
satnogs_ogg_source.block.yml
|
||||
satnogs_tcp_rigctl_msg_source.block.yml
|
||||
satnogs_udp_msg_sink.block.yml
|
||||
satnogs_udp_msg_source.block.yml
|
||||
satnogs_waterfall_sink.block.yml
|
||||
satnogs_whitening_ccsds.block.yml
|
||||
satnogs_whitening.block.yml
|
||||
satnogs.tree.yml
|
||||
)
|
||||
|
||||
if(${INCLUDE_DEBUG_BLOCKS})
|
||||
list(APPEND enabled_blocks ${debug_blocks})
|
||||
endif()
|
||||
|
||||
# Boston, MA 02110-1301, USA.
|
||||
install(FILES
|
||||
${enabled_blocks}
|
||||
DESTINATION share/gnuradio/grc/blocks
|
||||
satnogs_cw_matched_filter_ff.xml
|
||||
satnogs_morse_decoder.xml
|
||||
satnogs_morse_debug_source.xml
|
||||
satnogs_multi_format_msg_sink.xml
|
||||
satnogs_cw_to_symbol.xml
|
||||
satnogs_sine_matched_filter_ff.xml
|
||||
satnogs_udp_msg_source.xml
|
||||
satnogs_debug_msg_source.xml
|
||||
satnogs_json_to_ecss_src.xml
|
||||
satnogs_tcp_rigctl_msg_source.xml
|
||||
satnogs_frame_encoder.xml
|
||||
satnogs_doppler_correction_cc.xml
|
||||
satnogs_upsat_fsk_frame_acquisition.xml
|
||||
satnogs_upsat_fsk_frame_encoder.xml
|
||||
satnogs_whitening.xml
|
||||
satnogs_udp_msg_sink.xml
|
||||
satnogs_upsat_transmitter.xml
|
||||
satnogs_coarse_doppler_correction_cc.xml
|
||||
satnogs_debug_msg_source_raw.xml
|
||||
satnogs_ax25_encoder_mb.xml
|
||||
satnogs_ax25_decoder_bm.xml
|
||||
satnogs_qb50_deframer.xml DESTINATION share/gnuradio/grc/blocks
|
||||
)
|
||||
|
|
|
@ -1,37 +0,0 @@
|
|||
'[SatNOGS]':
|
||||
- Decoders:
|
||||
- variable_amsat_duv_decoder
|
||||
- variable_ax25_decoder
|
||||
- variable_ax100_decoder
|
||||
- variable_ieee802_15_4_variant_decoder
|
||||
- satnogs_morse_decoder
|
||||
- Satellites:
|
||||
- NOAA:
|
||||
- satnogs_noaa_apt_sink
|
||||
- METEOR:
|
||||
- satnogs_lrpt_decoder
|
||||
- satnogs_lrpt_sync
|
||||
- satnogs_ax25_encoder_mb
|
||||
- satnogs_coarse_doppler_correction_cc
|
||||
- satnogs_doppler_compensation
|
||||
- satnogs_doppler_correction_cc
|
||||
- satnogs_frame_decoder
|
||||
- satnogs_frame_file_sink
|
||||
- satnogs_iq_sink
|
||||
- satnogs_json_converter
|
||||
- satnogs_ogg_encoder
|
||||
- satnogs_ogg_source
|
||||
- satnogs_tcp_rigctl_msg_source
|
||||
- satnogs_udp_msg_sink
|
||||
- satnogs_udp_msg_source
|
||||
- satnogs_waterfall_sink
|
||||
- satnogs_whitening_ccsds
|
||||
- satnogs_whitening
|
||||
- Debug:
|
||||
- satnogs_cw_encoder
|
||||
- satnogs_cw_to_symbol
|
||||
- satnogs_debug_msg_source_raw
|
||||
- satnogs_debug_msg_source
|
||||
- satnogs_morse_debug_source
|
||||
- satnogs_multi_format_msg_sink
|
||||
|
|
@ -1,22 +0,0 @@
|
|||
id: variable_amsat_duv_decoder
|
||||
label: AMSAT DUV Decoder Definition
|
||||
flags: [show_id]
|
||||
|
||||
parameters:
|
||||
- id: control_symbol
|
||||
label: Control symbol
|
||||
dtype: string
|
||||
default: '0011111010'
|
||||
|
||||
- id: frame_len
|
||||
label: Maximum Frame Length
|
||||
dtype: int
|
||||
default: 96
|
||||
|
||||
value: ${satnogs.amsat_duv_decoder_make(control_symbol, frame_len)}
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
var_make: self.${id} = ${id} = satnogs.amsat_duv_decoder_make(${control_symbol}, ${frame_len})
|
||||
|
||||
file_format: 1
|
|
@ -1,49 +0,0 @@
|
|||
id: variable_ax100_decoder
|
||||
label: AX.100 Decoder Definition
|
||||
flags: [show_id]
|
||||
|
||||
parameters:
|
||||
- id: preamble
|
||||
label: Preamble
|
||||
dtype: raw
|
||||
default: [0x55, 0x55, 0x55, 0x55, 0x55]
|
||||
|
||||
- id: preamble_thrsh
|
||||
label: Preamble Threshold
|
||||
dtype: int
|
||||
default: 5
|
||||
|
||||
- id: sync_word
|
||||
label: Synchronization Word
|
||||
dtype: raw
|
||||
default: [0x31, 0xe5]
|
||||
|
||||
- id: sync_thrsh
|
||||
label: Synchronization Word Threshold
|
||||
dtype: int
|
||||
default: 3
|
||||
|
||||
- id: crc
|
||||
label: CRC
|
||||
dtype: raw
|
||||
default: 'satnogs.crc.CRC_NONE'
|
||||
|
||||
- id: whitening
|
||||
label: Whitening
|
||||
dtype: raw
|
||||
default: 'satnogs.whitening_sptr(None)'
|
||||
|
||||
- id: rs
|
||||
label: Reed Solomon
|
||||
dtype: bool
|
||||
default: 'True'
|
||||
options: ['True', 'False']
|
||||
option_labels: ['Enable', 'Disable']
|
||||
|
||||
value: ${satnogs.ax100_decoder_make(preamble, preamble_thrsh, sync_word, sync_thrsh, crc, whitening, rs)}
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
var_make: self.${id} = ${id} = satnogs.ax100_decoder_make(${preamble}, ${preamble_thrsh}, ${sync_word}, ${sync_thrsh}, ${crc}, ${whitening}, ${rs)}
|
||||
|
||||
file_format: 1
|
|
@ -1,48 +0,0 @@
|
|||
id: variable_ax25_decoder
|
||||
label: AX.25 Decoder Definition
|
||||
flags: [show_id]
|
||||
|
||||
parameters:
|
||||
- id: addr
|
||||
label: Receiver Callsign
|
||||
dtype: string
|
||||
default: 'GND'
|
||||
|
||||
- id: ssid
|
||||
label: Receiver SSID
|
||||
dtype: int
|
||||
default: 0
|
||||
|
||||
- id: descrambling
|
||||
label: G3RUH Descrambling
|
||||
dtype: bool
|
||||
default: 'True'
|
||||
options: ['True', 'False']
|
||||
option_labels: ['Enable', 'Disable']
|
||||
|
||||
- id: promisc
|
||||
label: Promiscuous mode
|
||||
dtype: bool
|
||||
default: 'True'
|
||||
options: ['True', 'False']
|
||||
option_labels: ['Enable', 'Disable']
|
||||
|
||||
- id: crc_check
|
||||
label: Perform CRC check
|
||||
dtype: bool
|
||||
default: 'True'
|
||||
options: ['True', 'False']
|
||||
option_labels: ['Enable', 'Disable']
|
||||
|
||||
- id: frame_len
|
||||
label: Maximum Frame Length
|
||||
dtype: int
|
||||
default: 512
|
||||
|
||||
value: ${satnogs.ax25_decoder_make(addr, ssid, promisc, descrambling, crc_check, frame_len)}
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
var_make: self.${id} = ${id} = satnogs.ax25_decoder_make(${addr}, ${ssid}, ${promisc}, ${descrambling}, ${crc_check}, ${frame_len})
|
||||
|
||||
file_format: 1
|
|
@ -0,0 +1,82 @@
|
|||
<?xml version="1.0"?>
|
||||
<block>
|
||||
<name>AX.25 Decoder</name>
|
||||
<key>satnogs_ax25_decoder_bm</key>
|
||||
<category>satnogs</category>
|
||||
<import>import satnogs</import>
|
||||
<make>satnogs.ax25_decoder_bm($addr, $ssid, $promisc, $descrambling, $max_frame_len, $n_sync_flags)</make>
|
||||
|
||||
<param>
|
||||
<name>Receiver Callsign</name>
|
||||
<key>addr</key>
|
||||
<value>'GND'</value>
|
||||
<type>string</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Receiver SSID</name>
|
||||
<key>ssid</key>
|
||||
<value>0</value>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
|
||||
<param>
|
||||
<name>Promiscuous mode</name>
|
||||
<key>promisc</key>
|
||||
<type>enum</type>
|
||||
<option>
|
||||
<name>No</name>
|
||||
<key>False</key>
|
||||
</option>
|
||||
<option>
|
||||
<name>Yes</name>
|
||||
<key>True</key>
|
||||
</option>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>G3RUH descrambling</name>
|
||||
<key>descrambling</key>
|
||||
<type>enum</type>
|
||||
<option>
|
||||
<name>Yes</name>
|
||||
<key>True</key>
|
||||
</option>
|
||||
<option>
|
||||
<name>No</name>
|
||||
<key>False</key>
|
||||
</option>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Maximum frame length</name>
|
||||
<key>max_frame_len</key>
|
||||
<value>256</value>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>AX.25 Leading SYNC flags Threshold</name>
|
||||
<key>n_sync_flags</key>
|
||||
<value>2</value>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<sink>
|
||||
<name>in</name>
|
||||
<type>byte</type>
|
||||
</sink>
|
||||
|
||||
<source>
|
||||
<name>pdu</name>
|
||||
<type>message</type>
|
||||
</source>
|
||||
|
||||
<source>
|
||||
<name>failed_pdu</name>
|
||||
<type>message</type>
|
||||
<optional>1</optional>
|
||||
</source>
|
||||
</block>
|
||||
|
|
@ -1,50 +0,0 @@
|
|||
id: satnogs_ax25_encoder_mb
|
||||
label: AX25 Encoder
|
||||
|
||||
parameters:
|
||||
- id: dest_addr
|
||||
label: Destination Callsign
|
||||
dtype: string
|
||||
|
||||
- id: dest_ssid
|
||||
label: Destination SSID
|
||||
dtype: int
|
||||
default: 0
|
||||
|
||||
- id: src_addr
|
||||
label: Source Callsign
|
||||
dtype: string
|
||||
|
||||
- id: src_ssid
|
||||
label: Source SSID
|
||||
dtype: int
|
||||
default: 0
|
||||
|
||||
- id: preamble_len
|
||||
label: Preamble Length
|
||||
dtype: int
|
||||
default: 16
|
||||
|
||||
- id: postamble_len
|
||||
label: Postamble Length
|
||||
dtype: int
|
||||
default: 16
|
||||
|
||||
- id: scramble
|
||||
label: G3RUH Scrambling
|
||||
dtype: bool
|
||||
default: 'True'
|
||||
options: ['True', 'False']
|
||||
option_labels: ['Enable', 'Disable']
|
||||
|
||||
outputs:
|
||||
- label: out
|
||||
domain: stream
|
||||
dtype: byte
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
make: satnogs.ax25_encoder_mb(${dest_addr}, ${dest_ssid}, ${src_addr}, ${src_ssid},
|
||||
${preamble_len}, ${postamble_len}, ${scramble})
|
||||
|
||||
file_format: 1
|
|
@ -0,0 +1,70 @@
|
|||
<?xml version="1.0"?>
|
||||
<block>
|
||||
<name>AX.25 Encoder</name>
|
||||
<key>satnogs_ax25_encoder_mb</key>
|
||||
<category>satnogs</category>
|
||||
<import>import satnogs</import>
|
||||
<make>satnogs.ax25_encoder_mb($dest_addr, $dest_ssid, $src_addr, $src_ssid, $preamble_len, $postamble_len, $scramble)</make>
|
||||
|
||||
<param>
|
||||
<name>Destination Callsign</name>
|
||||
<key>dest_addr</key>
|
||||
<type>string</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Destination SSID</name>
|
||||
<key>dest_ssid</key>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Source Callsign</name>
|
||||
<key>src_addr</key>
|
||||
<type>string</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Source SSID</name>
|
||||
<key>src_ssid</key>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Preamble Length</name>
|
||||
<key>preamble_len</key>
|
||||
<value>16</value>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Postamble Length</name>
|
||||
<key>postamble_len</key>
|
||||
<value>16</value>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>G3RUH Scrambling</name>
|
||||
<key>scramble</key>
|
||||
<type>enum</type>
|
||||
<option>
|
||||
<name>Yes</name>
|
||||
<key>True</key>
|
||||
</option>
|
||||
<option>
|
||||
<name>No</name>
|
||||
<key>False</key>
|
||||
</option>
|
||||
</param>
|
||||
|
||||
<sink>
|
||||
<name>info</name>
|
||||
<type>message</type>
|
||||
</sink>
|
||||
|
||||
<source>
|
||||
<name>out</name>
|
||||
<type>byte</type>
|
||||
</source>
|
||||
</block>
|
|
@ -1,38 +0,0 @@
|
|||
id: satnogs_coarse_doppler_correction_cc
|
||||
label: Doppler Correction (Coarse)
|
||||
|
||||
parameters:
|
||||
- id: target_freq
|
||||
label: Target frequency
|
||||
dtype: real
|
||||
default: 0.0
|
||||
|
||||
- id: offset
|
||||
label: Offset
|
||||
dtype: real
|
||||
default: 0.0
|
||||
|
||||
- id: sampling_rate
|
||||
label: Sample Rate
|
||||
dtype: real
|
||||
default: samp_rate
|
||||
|
||||
inputs:
|
||||
- label: in
|
||||
domain: stream
|
||||
dtype: complex
|
||||
|
||||
- id: freq
|
||||
domain: message
|
||||
optional: true
|
||||
|
||||
outputs:
|
||||
- label: out
|
||||
domain: stream
|
||||
dtype: complex
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
make: satnogs.coarse_doppler_correction_cc(${target_freq}, ${offset}, ${sampling_rate})
|
||||
|
||||
file_format: 1
|
|
@ -0,0 +1,37 @@
|
|||
<?xml version="1.0"?>
|
||||
<block>
|
||||
<name>Coarse Doppler Correction</name>
|
||||
<key>satnogs_coarse_doppler_correction_cc</key>
|
||||
<category>satnogs</category>
|
||||
<import>import satnogs</import>
|
||||
<make>satnogs.coarse_doppler_correction_cc($target_freq, $sampling_rate)</make>
|
||||
<callback>set_new_freq_locked($target_freq)</callback>
|
||||
|
||||
<param>
|
||||
<name>Target Frequency</name>
|
||||
<key>target_freq</key>
|
||||
<type>real</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Sample Rate</name>
|
||||
<key>sampling_rate</key>
|
||||
<value>samp_rate</value>
|
||||
<type>real</type>
|
||||
</param>
|
||||
|
||||
<sink>
|
||||
<name>freq</name>
|
||||
<type>message</type>
|
||||
</sink>
|
||||
|
||||
<sink>
|
||||
<name>in</name>
|
||||
<type>complex</type>
|
||||
</sink>
|
||||
|
||||
<source>
|
||||
<name>out</name>
|
||||
<type>complex</type>
|
||||
</source>
|
||||
</block>
|
|
@ -1,34 +0,0 @@
|
|||
id: satnogs_cw_encoder
|
||||
label: CW Encoder
|
||||
|
||||
parameters:
|
||||
|
||||
- id: samp_rate
|
||||
label: Sample Rate
|
||||
dtype: real
|
||||
default: samp_rate
|
||||
|
||||
- id: cw_freq
|
||||
label: CW Tone Frequency
|
||||
dtype: real
|
||||
default: 700
|
||||
|
||||
- id: wpm
|
||||
label: Words per minute
|
||||
dtype: int
|
||||
default: 20
|
||||
|
||||
inputs:
|
||||
- domain: message
|
||||
id: symbol
|
||||
|
||||
outputs:
|
||||
- label: out
|
||||
domain: stream
|
||||
dtype: complex
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
make: satnogs.cw_encoder(${samp_rate}, ${cw_freq}, ${wpm})
|
||||
|
||||
file_format: 1
|
|
@ -0,0 +1,58 @@
|
|||
<?xml version="1.0"?>
|
||||
<block>
|
||||
<name>CW Matched Filter</name>
|
||||
<key>satnogs_cw_matched_filter_ff</key>
|
||||
<category>satnogs</category>
|
||||
<import>import satnogs</import>
|
||||
<make>satnogs.cw_matched_filter_ff($sampling_rate, $carrier_freq, $wpm, $energy)</make>
|
||||
<callback>set_new_freq_locked($carrier_freq)</callback>
|
||||
|
||||
<param>
|
||||
<name>Sampling Rate</name>
|
||||
<key>sampling_rate</key>
|
||||
<type>real</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Audio Frequency (Hz)</name>
|
||||
<key>carrier_freq</key>
|
||||
<type>real</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Words per Minute</name>
|
||||
<key>wpm</key>
|
||||
<value>20</value>
|
||||
<type>int</type>
|
||||
</param>
|
||||
|
||||
<param>
|
||||
<name>Compute Energy</name>
|
||||
<key>energy</key>
|
||||
<type>enum</type>
|
||||
<option>
|
||||
<name>No</name>
|
||||
<key>False</key>
|
||||
</option>
|
||||
<option>
|
||||
<name>Yes</name>
|
||||
<key>True</key>
|
||||
</option>
|
||||
</param>
|
||||
|
||||
<sink>
|
||||
<name>freq</name>
|
||||
<type>message</type>
|
||||
<optional>1</optional>
|
||||
</sink>
|
||||
|
||||
<sink>
|
||||
<name>in</name>
|
||||
<type>float</type>
|
||||
</sink>
|
||||
|
||||
<source>
|
||||
<name>out</name>
|
||||
<type>float</type>
|
||||
</source>
|
||||
</block>
|
|
@ -1,48 +0,0 @@
|
|||
id: satnogs_cw_to_symbol
|
||||
label: CW to Symbol
|
||||
|
||||
parameters:
|
||||
- id: samp_rate
|
||||
label: Sample Rate
|
||||
dtype: real
|
||||
default: samp_rate
|
||||
|
||||
- id: threshold
|
||||
label: Activation Threshold
|
||||
dtype: real
|
||||
|
||||
- id: conf_level
|
||||
label: Confidence Level
|
||||
dtype: real
|
||||
default: 0.9
|
||||
|
||||
- id: wpm
|
||||
label: Words per Minute
|
||||
dtype: int
|
||||
default: 20
|
||||
|
||||
- id: hysteresis
|
||||
label: Hysteresis
|
||||
dtype: int
|
||||
default: 0
|
||||
|
||||
inputs:
|
||||
- label: in
|
||||
domain: stream
|
||||
dtype: float
|
||||
|
||||
- domain: message
|
||||
id: act_threshold
|
||||
optional: true
|
||||
|
||||
outputs:
|
||||
- domain: message
|
||||
id: out
|
||||
|
||||
templates:
|
||||
imports: import satnogs
|
||||
make: satnogs.cw_to_symbol(${samp_rate}, ${threshold}, ${conf_level}, ${wpm}, ${hysteresis})
|
||||
callbacks:
|
||||
- set_act_threshold(${threshold})
|
||||
|
||||
file_format: 1
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue