changes to the build system
1
.gitignore
vendored
@ -8,3 +8,4 @@ build/
|
|||||||
.DS_Store
|
.DS_Store
|
||||||
sdrpp_v0.2.5_beta_x64
|
sdrpp_v0.2.5_beta_x64
|
||||||
sdrpp_v0.2.5_beta_x64_new_wf
|
sdrpp_v0.2.5_beta_x64_new_wf
|
||||||
|
root_dev/
|
@ -1,19 +1,44 @@
|
|||||||
cmake_minimum_required(VERSION 3.13)
|
cmake_minimum_required(VERSION 3.13)
|
||||||
project(sdrpp)
|
project(sdrpp)
|
||||||
|
|
||||||
|
option(OPT_BUILD_RTL_TCP_SOURCE "Build RTL-TCP Source Module (no dependencies required)" ON)
|
||||||
|
option(OPT_BUILD_SPYSERVER_SOURCE "Build SpyServer Source Module (no dependencies required)" ON)
|
||||||
|
option(OPT_BUILD_SOAPY_SOURCE "Build SoapySDR Source Module (Depedencies: soapysdr)" ON)
|
||||||
|
option(OPT_BUILD_AIRSPYHF_SOURCE "Build Airspy HF+ Source Module (Depedencies: libairspyhf)" ON)
|
||||||
|
option(OPT_BUILD_PLUTOSDR_SOURCE "Build PlutoSDR Source Module (Depedencies: libiio, libad9361)" ON)
|
||||||
|
option(OPT_BUILD_AUDIO_SINK "Build Audio Sink Module (Depedencies: portaudio)" ON)
|
||||||
|
|
||||||
# Core of SDR++
|
# Core of SDR++
|
||||||
add_subdirectory("core")
|
add_subdirectory("core")
|
||||||
|
|
||||||
# Cross platform modules
|
# Base modules
|
||||||
add_subdirectory("radio")
|
add_subdirectory("radio")
|
||||||
add_subdirectory("recorder")
|
add_subdirectory("recorder")
|
||||||
add_subdirectory("soapy_source")
|
|
||||||
add_subdirectory("airspyhf_source")
|
# Source modules
|
||||||
#add_subdirectory("file_source")
|
if (OPT_BUILD_RTL_TCP_SOURCE)
|
||||||
add_subdirectory("rtl_tcp_source")
|
add_subdirectory("rtl_tcp_source")
|
||||||
add_subdirectory("audio_sink")
|
endif (OPT_BUILD_RTL_TCP_SOURCE)
|
||||||
#add_subdirectory("rx888_source")
|
|
||||||
|
if (OPT_BUILD_SPYSERVER_SOURCE)
|
||||||
|
add_subdirectory("spyserver_source")
|
||||||
|
endif (OPT_BUILD_SPYSERVER_SOURCE)
|
||||||
|
|
||||||
|
if (OPT_BUILD_SOAPY_SOURCE)
|
||||||
|
add_subdirectory("soapy_source")
|
||||||
|
endif (OPT_BUILD_SOAPY_SOURCE)
|
||||||
|
|
||||||
|
if (OPT_BUILD_AIRSPYHF_SOURCE)
|
||||||
|
add_subdirectory("airspyhf_source")
|
||||||
|
endif (OPT_BUILD_AIRSPYHF_SOURCE)
|
||||||
|
|
||||||
|
if (OPT_BUILD_PLUTOSDR_SOURCE)
|
||||||
add_subdirectory("plutosdr_source")
|
add_subdirectory("plutosdr_source")
|
||||||
|
endif (OPT_BUILD_PLUTOSDR_SOURCE)
|
||||||
|
|
||||||
|
if (OPT_BUILD_AUDIO_SINK)
|
||||||
|
add_subdirectory("audio_sink")
|
||||||
|
endif (OPT_BUILD_AUDIO_SINK)
|
||||||
|
|
||||||
if (MSVC)
|
if (MSVC)
|
||||||
set(CMAKE_CXX_FLAGS "-O2 /std:c++17 /EHsc")
|
set(CMAKE_CXX_FLAGS "-O2 /std:c++17 /EHsc")
|
||||||
|
@ -5,6 +5,7 @@
|
|||||||
#include <signal_path/signal_path.h>
|
#include <signal_path/signal_path.h>
|
||||||
#include <core.h>
|
#include <core.h>
|
||||||
#include <gui/style.h>
|
#include <gui/style.h>
|
||||||
|
#include <config.h>
|
||||||
#include <libairspyhf/airspyhf.h>
|
#include <libairspyhf/airspyhf.h>
|
||||||
|
|
||||||
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
||||||
@ -17,6 +18,8 @@ SDRPP_MOD_INFO {
|
|||||||
/* Max instances */ 1
|
/* Max instances */ 1
|
||||||
};
|
};
|
||||||
|
|
||||||
|
//ConfigManager config;
|
||||||
|
|
||||||
const char* AGG_MODES_STR = "Off\0Low\0High\0";
|
const char* AGG_MODES_STR = "Off\0Low\0High\0";
|
||||||
|
|
||||||
class AirspyHFSourceModule : public ModuleManager::Instance {
|
class AirspyHFSourceModule : public ModuleManager::Instance {
|
||||||
@ -36,7 +39,10 @@ public:
|
|||||||
handler.stream = &stream;
|
handler.stream = &stream;
|
||||||
|
|
||||||
refresh();
|
refresh();
|
||||||
selectFirst();
|
|
||||||
|
// config.aquire();
|
||||||
|
// std::string serString = config.conf["device"];
|
||||||
|
// config.release();
|
||||||
|
|
||||||
sigpath::sourceManager.registerSource("Airspy HF+", &handler);
|
sigpath::sourceManager.registerSource("Airspy HF+", &handler);
|
||||||
}
|
}
|
||||||
@ -92,9 +98,10 @@ public:
|
|||||||
std::string str = buf;
|
std::string str = buf;
|
||||||
if (serial == str) {
|
if (serial == str) {
|
||||||
selectBySerial(devList[i]);
|
selectBySerial(devList[i]);
|
||||||
break;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
selectFirst();
|
||||||
}
|
}
|
||||||
|
|
||||||
void selectBySerial(uint64_t serial) {
|
void selectBySerial(uint64_t serial) {
|
||||||
@ -287,7 +294,12 @@ private:
|
|||||||
};
|
};
|
||||||
|
|
||||||
MOD_EXPORT void _INIT_() {
|
MOD_EXPORT void _INIT_() {
|
||||||
// Do your one time init here
|
// config.setPath(ROOT_DIR "/airspyhf_config.json");
|
||||||
|
// json defConf;
|
||||||
|
// defConf["device"] = "";
|
||||||
|
// defConf["devices"] = json::object();
|
||||||
|
// config.load(defConf);
|
||||||
|
// config.enableAutoSave();
|
||||||
}
|
}
|
||||||
|
|
||||||
MOD_EXPORT ModuleManager::Instance* _CREATE_INSTANCE_(std::string name) {
|
MOD_EXPORT ModuleManager::Instance* _CREATE_INSTANCE_(std::string name) {
|
||||||
@ -299,5 +311,6 @@ MOD_EXPORT void _DELETE_INSTANCE_(ModuleManager::Instance* instance) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
MOD_EXPORT void _END_() {
|
MOD_EXPORT void _END_() {
|
||||||
// Do your one shutdown here
|
// config.disableAutoSave();
|
||||||
|
// config.save();
|
||||||
}
|
}
|
@ -6,20 +6,6 @@
|
|||||||
|
|
||||||
using nlohmann::json;
|
using nlohmann::json;
|
||||||
|
|
||||||
#define DEV_BUILD
|
|
||||||
|
|
||||||
#define SDRPP_RESOURCE_DIR "/usr/local/"
|
|
||||||
|
|
||||||
#ifndef ROOT_DIR
|
|
||||||
#ifdef DEV_BUILD
|
|
||||||
#define ROOT_DIR "../root_dev"
|
|
||||||
#elif _WIN32
|
|
||||||
#define ROOT_DIR "."
|
|
||||||
#else
|
|
||||||
#define ROOT_DIR "/etc/sdrpp"
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
class ConfigManager {
|
class ConfigManager {
|
||||||
public:
|
public:
|
||||||
ConfigManager();
|
ConfigManager();
|
||||||
@ -32,20 +18,11 @@ public:
|
|||||||
void aquire();
|
void aquire();
|
||||||
void release(bool changed = false);
|
void release(bool changed = false);
|
||||||
|
|
||||||
// static void setResourceDir(std::string path);
|
|
||||||
// static std::string getResourceDir();
|
|
||||||
|
|
||||||
// static void setConfigDir(std::string path);
|
|
||||||
// static std::string getConfigDir();
|
|
||||||
|
|
||||||
json conf;
|
json conf;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static void autoSaveWorker(ConfigManager* _this);
|
static void autoSaveWorker(ConfigManager* _this);
|
||||||
|
|
||||||
//static std::string resDir;
|
|
||||||
//static std::string configDir;
|
|
||||||
|
|
||||||
std::string path = "";
|
std::string path = "";
|
||||||
bool changed = false;
|
bool changed = false;
|
||||||
bool autoSaveEnabled = false;
|
bool autoSaveEnabled = false;
|
||||||
|
@ -14,6 +14,7 @@
|
|||||||
#include <stb_image.h>
|
#include <stb_image.h>
|
||||||
#include <config.h>
|
#include <config.h>
|
||||||
#include <core.h>
|
#include <core.h>
|
||||||
|
#include <options.h>
|
||||||
#include <duktape/duktape.h>
|
#include <duktape/duktape.h>
|
||||||
#include <duktape/duk_console.h>
|
#include <duktape/duk_console.h>
|
||||||
|
|
||||||
@ -63,16 +64,19 @@ duk_ret_t test_func(duk_context *ctx) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// main
|
// main
|
||||||
int sdrpp_main() {
|
int sdrpp_main(int argc, char *argv[]) {
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
//FreeConsole();
|
//FreeConsole();
|
||||||
// ConfigManager::setResourceDir("./res");
|
// ConfigManager::setResourceDir("./res");
|
||||||
// ConfigManager::setConfigDir(".");
|
// ConfigManager::setConfigDir(".");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
spdlog::info("SDR++ v" VERSION_STR);
|
spdlog::info("SDR++ v" VERSION_STR);
|
||||||
|
|
||||||
|
// Load default options and parse command line
|
||||||
|
options::loadDefaults();
|
||||||
|
if (!options::parse(argc, argv)) { return -1; }
|
||||||
|
|
||||||
// ======== DEFAULT CONFIG ========
|
// ======== DEFAULT CONFIG ========
|
||||||
json defConfig;
|
json defConfig;
|
||||||
defConfig["bandColors"]["amateur"] = "#FF0000FF";
|
defConfig["bandColors"]["amateur"] = "#FF0000FF";
|
||||||
@ -114,8 +118,8 @@ int sdrpp_main() {
|
|||||||
defConfig["windowSize"]["w"] = 1280;
|
defConfig["windowSize"]["w"] = 1280;
|
||||||
|
|
||||||
// Load config
|
// Load config
|
||||||
spdlog::info("Loading config");
|
spdlog::info("Loading config {0}");
|
||||||
core::configManager.setPath(ROOT_DIR "/config.json");
|
core::configManager.setPath(options::opts.root + "/config.json");
|
||||||
core::configManager.load(defConfig);
|
core::configManager.load(defConfig);
|
||||||
core::configManager.enableAutoSave();
|
core::configManager.enableAutoSave();
|
||||||
|
|
||||||
@ -153,7 +157,7 @@ int sdrpp_main() {
|
|||||||
|
|
||||||
// Load app icon
|
// Load app icon
|
||||||
GLFWimage icons[10];
|
GLFWimage icons[10];
|
||||||
icons[0].pixels = stbi_load(((std::string)(ROOT_DIR "/res/icons/sdrpp.png")).c_str(), &icons[0].width, &icons[0].height, 0, 4);
|
icons[0].pixels = stbi_load(((std::string)(options::opts.root + "/res/icons/sdrpp.png")).c_str(), &icons[0].width, &icons[0].height, 0, 4);
|
||||||
icons[1].pixels = (unsigned char*)malloc(16 * 16 * 4); icons[1].width = icons[1].height = 16;
|
icons[1].pixels = (unsigned char*)malloc(16 * 16 * 4); icons[1].width = icons[1].height = 16;
|
||||||
icons[2].pixels = (unsigned char*)malloc(24 * 24 * 4); icons[2].width = icons[2].height = 24;
|
icons[2].pixels = (unsigned char*)malloc(24 * 24 * 4); icons[2].width = icons[2].height = 24;
|
||||||
icons[3].pixels = (unsigned char*)malloc(32 * 32 * 4); icons[3].width = icons[3].height = 32;
|
icons[3].pixels = (unsigned char*)malloc(32 * 32 * 4); icons[3].width = icons[3].height = 32;
|
||||||
@ -204,11 +208,11 @@ int sdrpp_main() {
|
|||||||
|
|
||||||
LoadingScreen::show("Loading band plans");
|
LoadingScreen::show("Loading band plans");
|
||||||
spdlog::info("Loading band plans");
|
spdlog::info("Loading band plans");
|
||||||
bandplan::loadFromDir(ROOT_DIR "/bandplans");
|
bandplan::loadFromDir(options::opts.root + "/bandplans");
|
||||||
|
|
||||||
LoadingScreen::show("Loading band plan colors");
|
LoadingScreen::show("Loading band plan colors");
|
||||||
spdlog::info("Loading band plans color table");
|
spdlog::info("Loading band plans color table");
|
||||||
bandplan::loadColorTable(ROOT_DIR "/band_colors.json");
|
bandplan::loadColorTable(options::opts.root + "/band_colors.json");
|
||||||
|
|
||||||
windowInit();
|
windowInit();
|
||||||
|
|
||||||
|
@ -12,4 +12,4 @@ namespace core {
|
|||||||
void setInputSampleRate(double samplerate);
|
void setInputSampleRate(double samplerate);
|
||||||
};
|
};
|
||||||
|
|
||||||
int sdrpp_main();
|
int sdrpp_main(int argc, char *argv[]);
|
@ -2,6 +2,7 @@
|
|||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <GL/glew.h>
|
#include <GL/glew.h>
|
||||||
#include <config.h>
|
#include <config.h>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
#define STB_IMAGE_IMPLEMENTATION
|
#define STB_IMAGE_IMPLEMENTATION
|
||||||
#include <imgui/stb_image.h>
|
#include <imgui/stb_image.h>
|
||||||
@ -31,13 +32,13 @@ namespace icons {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void load() {
|
void load() {
|
||||||
LOGO = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/sdrpp.png");
|
LOGO = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/sdrpp.png");
|
||||||
PLAY = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/play.png");
|
PLAY = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/play.png");
|
||||||
STOP = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/stop.png");
|
STOP = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/stop.png");
|
||||||
MENU = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/menu.png");
|
MENU = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/menu.png");
|
||||||
MUTED = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/muted.png");
|
MUTED = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/muted.png");
|
||||||
UNMUTED = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/unmuted.png");
|
UNMUTED = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/unmuted.png");
|
||||||
NORMAL_TUNING = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/normal_tuning.png");
|
NORMAL_TUNING = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/normal_tuning.png");
|
||||||
CENTER_TUNING = (ImTextureID)(uintptr_t)loadTexture(ROOT_DIR "/res/icons/center_tuning.png");
|
CENTER_TUNING = (ImTextureID)(uintptr_t)loadTexture(options::opts.root + "/res/icons/center_tuning.png");
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -30,6 +30,7 @@
|
|||||||
#include <filesystem>
|
#include <filesystem>
|
||||||
#include <signal_path/source.h>
|
#include <signal_path/source.h>
|
||||||
#include <gui/dialogs/loading_screen.h>
|
#include <gui/dialogs/loading_screen.h>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
// const int FFTSizes[] = {
|
// const int FFTSizes[] = {
|
||||||
// 65536,
|
// 65536,
|
||||||
@ -143,8 +144,8 @@ void windowInit() {
|
|||||||
spdlog::info("Loading modules");
|
spdlog::info("Loading modules");
|
||||||
|
|
||||||
// Load modules from /module directory
|
// Load modules from /module directory
|
||||||
if (std::filesystem::is_directory(ROOT_DIR "/modules")) {
|
if (std::filesystem::is_directory(options::opts.root + "/modules")) {
|
||||||
for (const auto & file : std::filesystem::directory_iterator(ROOT_DIR "/modules")) {
|
for (const auto & file : std::filesystem::directory_iterator(options::opts.root + "/modules")) {
|
||||||
std::string path = file.path().generic_string();
|
std::string path = file.path().generic_string();
|
||||||
if (file.path().extension().generic_string() != SDRPP_MOD_EXTENTSION) {
|
if (file.path().extension().generic_string() != SDRPP_MOD_EXTENTSION) {
|
||||||
continue;
|
continue;
|
||||||
@ -595,7 +596,6 @@ void drawWindow() {
|
|||||||
gui::waterfall.setWaterfallMin(fftMin);
|
gui::waterfall.setWaterfallMin(fftMin);
|
||||||
gui::waterfall.setWaterfallMax(fftMax);
|
gui::waterfall.setWaterfallMax(fftMax);
|
||||||
|
|
||||||
|
|
||||||
ImGui::End();
|
ImGui::End();
|
||||||
|
|
||||||
if (showCredits) {
|
if (showCredits) {
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
#include <imgui.h>
|
#include <imgui.h>
|
||||||
#include <imgui_internal.h>
|
#include <imgui_internal.h>
|
||||||
#include <config.h>
|
#include <config.h>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
namespace style {
|
namespace style {
|
||||||
ImFont* baseFont;
|
ImFont* baseFont;
|
||||||
@ -16,9 +17,9 @@ namespace style {
|
|||||||
ImGui::GetStyle().PopupRounding = 0.0f;
|
ImGui::GetStyle().PopupRounding = 0.0f;
|
||||||
ImGui::GetStyle().ScrollbarRounding = 0.0f;
|
ImGui::GetStyle().ScrollbarRounding = 0.0f;
|
||||||
|
|
||||||
baseFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(ROOT_DIR "/res/fonts/Roboto-Medium.ttf")).c_str(), 16.0f);
|
baseFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(options::opts.root + "/res/fonts/Roboto-Medium.ttf")).c_str(), 16.0f);
|
||||||
bigFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(ROOT_DIR "/res/fonts/Roboto-Medium.ttf")).c_str(), 42.0f);
|
bigFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(options::opts.root + "/res/fonts/Roboto-Medium.ttf")).c_str(), 42.0f);
|
||||||
hugeFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(ROOT_DIR "/res/fonts/Roboto-Medium.ttf")).c_str(), 128.0f);
|
hugeFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(options::opts.root + "/res/fonts/Roboto-Medium.ttf")).c_str(), 128.0f);
|
||||||
|
|
||||||
ImGui::StyleColorsDark();
|
ImGui::StyleColorsDark();
|
||||||
//ImGui::StyleColorsLight();
|
//ImGui::StyleColorsLight();
|
||||||
@ -36,9 +37,9 @@ namespace style {
|
|||||||
ImGui::GetStyle().PopupRounding = 0.0f;
|
ImGui::GetStyle().PopupRounding = 0.0f;
|
||||||
ImGui::GetStyle().ScrollbarRounding = 0.0f;
|
ImGui::GetStyle().ScrollbarRounding = 0.0f;
|
||||||
|
|
||||||
baseFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(ROOT_DIR "/res/fonts/Roboto-Medium.ttf")).c_str(), 16.0f);
|
baseFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(options::opts.root + "/res/fonts/Roboto-Medium.ttf")).c_str(), 16.0f);
|
||||||
bigFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(ROOT_DIR "/res/fonts/Roboto-Medium.ttf")).c_str(), 42.0f);
|
bigFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(options::opts.root + "/res/fonts/Roboto-Medium.ttf")).c_str(), 42.0f);
|
||||||
hugeFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(ROOT_DIR "/res/fonts/Roboto-Medium.ttf")).c_str(), 128.0f);
|
hugeFont = ImGui::GetIO().Fonts->AddFontFromFileTTF(((std::string)(options::opts.root + "/res/fonts/Roboto-Medium.ttf")).c_str(), 128.0f);
|
||||||
|
|
||||||
ImGui::StyleColorsDark();
|
ImGui::StyleColorsDark();
|
||||||
|
|
||||||
|
@ -1,7 +1,29 @@
|
|||||||
#include <options.h>
|
#include <options.h>
|
||||||
|
#include <spdlog/spdlog.h>
|
||||||
|
|
||||||
namespace options {
|
namespace options {
|
||||||
void parse(char** argv, int argc) {
|
CMDLineOptions opts;
|
||||||
|
|
||||||
|
void loadDefaults() {
|
||||||
|
#ifdef _WIN32
|
||||||
|
opts.root = ".";
|
||||||
|
#else
|
||||||
|
opts.root = "~/.sdrpp/";
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
bool parse(int argc, char *argv[]) {
|
||||||
|
for (int i = 1; i < argc; i++) {
|
||||||
|
char* arg = argv[i];
|
||||||
|
if (!strcmp(arg, "-r") || !strcmp(arg, "--root")) {
|
||||||
|
if (i == argc - 1) { return false; }
|
||||||
|
opts.root = argv[++i];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
spdlog::error("Invalid command line option: {0}", arg);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,13 +1,14 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
#include <string>
|
#include <string>
|
||||||
|
#include <new_module.h>
|
||||||
|
|
||||||
namespace options {
|
namespace options {
|
||||||
struct CMDLineOptions {
|
struct CMDLineOptions {
|
||||||
std::string root;
|
std::string root;
|
||||||
bool help;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
CMDLineOptions opts;
|
SDRPP_EXPORT CMDLineOptions opts;
|
||||||
|
|
||||||
void parse(char** argv, int argc);
|
void loadDefaults();
|
||||||
|
bool parse(int argc, char *argv[]);
|
||||||
}
|
}
|
4
create_root.bat
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
echo OFF
|
||||||
|
|
||||||
|
mkdir root_dev
|
||||||
|
Xcopy root root_dev /E /H /C /I
|
3
create_root.sh
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
|
||||||
|
cp -r root root_dev
|
@ -7,6 +7,7 @@
|
|||||||
#include <gui/style.h>
|
#include <gui/style.h>
|
||||||
#include <iio.h>
|
#include <iio.h>
|
||||||
#include <ad9361.h>
|
#include <ad9361.h>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
||||||
|
|
||||||
@ -262,7 +263,7 @@ MOD_EXPORT void _INIT_() {
|
|||||||
defConf["sampleRate"] = 4000000.0f;
|
defConf["sampleRate"] = 4000000.0f;
|
||||||
defConf["gainMode"] = 0;
|
defConf["gainMode"] = 0;
|
||||||
defConf["gain"] = 0.0f;
|
defConf["gain"] = 0.0f;
|
||||||
config.setPath(ROOT_DIR "/plutosdr_source_config.json");
|
config.setPath(options::opts.root + "/plutosdr_source_config.json");
|
||||||
config.load(defConf);
|
config.load(defConf);
|
||||||
config.enableAutoSave();
|
config.enableAutoSave();
|
||||||
}
|
}
|
||||||
|
@ -1,6 +0,0 @@
|
|||||||
echo OFF
|
|
||||||
copy /b/v/y build\Release\* root\
|
|
||||||
copy /b/v/y build\radio\Release\radio.dll root\modules\radio.dll
|
|
||||||
copy /b/v/y build\recorder\Release\recorder.dll root\modules\recorder.dll
|
|
||||||
copy /b/v/y build\rtl_tcp_source\Release\rtl_tcp_source.dll root\modules\rtl_tcp_source.dll
|
|
||||||
copy /b/v/y build\soapy\Release\soapy.dll root\modules\soapy.dll
|
|
@ -1,3 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
|
|
||||||
cp build/*/*.so root/modules
|
|
@ -14,6 +14,7 @@
|
|||||||
#include <dsb_demod.h>
|
#include <dsb_demod.h>
|
||||||
#include <raw_demod.h>
|
#include <raw_demod.h>
|
||||||
#include <cw_demod.h>
|
#include <cw_demod.h>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
||||||
|
|
||||||
@ -197,7 +198,7 @@ private:
|
|||||||
|
|
||||||
MOD_EXPORT void _INIT_() {
|
MOD_EXPORT void _INIT_() {
|
||||||
json def = json({});
|
json def = json({});
|
||||||
config.setPath(ROOT_DIR "/radio_config.json");
|
config.setPath(options::opts.root + "/radio_config.json");
|
||||||
config.load(def);
|
config.load(def);
|
||||||
config.enableAutoSave();
|
config.enableAutoSave();
|
||||||
}
|
}
|
||||||
|
@ -12,6 +12,7 @@
|
|||||||
#include <config.h>
|
#include <config.h>
|
||||||
#include <gui/style.h>
|
#include <gui/style.h>
|
||||||
#include <regex>
|
#include <regex>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
||||||
|
|
||||||
@ -44,7 +45,7 @@ void sampleRateChanged(void* ctx, double sampleRate, int blockSize) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string expandString(std::string input) {
|
std::string expandString(std::string input) {
|
||||||
input = std::regex_replace(input, std::regex("%ROOT%"), ROOT_DIR);
|
input = std::regex_replace(input, std::regex("%ROOT%"), options::opts.root);
|
||||||
return std::regex_replace(input, std::regex("//"), "/");
|
return std::regex_replace(input, std::regex("//"), "/");
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -306,7 +307,7 @@ struct RecorderContext_t {
|
|||||||
|
|
||||||
MOD_EXPORT void _INIT_() {
|
MOD_EXPORT void _INIT_() {
|
||||||
json def = json({});
|
json def = json({});
|
||||||
config.setPath(ROOT_DIR "/recorder_config.json");
|
config.setPath(options::opts.root + "/recorder_config.json");
|
||||||
config.load(def);
|
config.load(def);
|
||||||
config.enableAutoSave();
|
config.enableAutoSave();
|
||||||
}
|
}
|
||||||
|
@ -1,43 +0,0 @@
|
|||||||
{
|
|
||||||
"audio": {
|
|
||||||
"Radio": {
|
|
||||||
"device": "CABLE Input (VB-Audio Virtual Cable)",
|
|
||||||
"sampleRate": 48000.0,
|
|
||||||
"volume": 0.42578125
|
|
||||||
},
|
|
||||||
"Radio 1": {
|
|
||||||
"device": "CABLE-A Input (VB-Audio Cable A)",
|
|
||||||
"sampleRate": 48000.0,
|
|
||||||
"volume": 1.0
|
|
||||||
},
|
|
||||||
"Radio 2": {
|
|
||||||
"device": "CABLE Input (VB-Audio Virtual Cable)",
|
|
||||||
"sampleRate": 48000.0,
|
|
||||||
"volume": 1.0
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"bandPlan": "General",
|
|
||||||
"bandPlanEnabled": true,
|
|
||||||
"fftHeight": 300,
|
|
||||||
"frequency": 98391106,
|
|
||||||
"max": 0.0,
|
|
||||||
"maximized": false,
|
|
||||||
"menuOrder": [
|
|
||||||
"Source",
|
|
||||||
"Radio",
|
|
||||||
"Recorder",
|
|
||||||
"Audio",
|
|
||||||
"Scripting",
|
|
||||||
"Band Plan",
|
|
||||||
"Display"
|
|
||||||
],
|
|
||||||
"menuWidth": 300,
|
|
||||||
"min": -72.05882263183594,
|
|
||||||
"showWaterfall": true,
|
|
||||||
"source": "",
|
|
||||||
"sourceSettings": {},
|
|
||||||
"windowSize": {
|
|
||||||
"h": 720,
|
|
||||||
"w": 1280
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,6 +0,0 @@
|
|||||||
{
|
|
||||||
"Radio": "./modules/radio.dll",
|
|
||||||
"Recorder": "./modules/recorder.dll",
|
|
||||||
"Soapy": "./modules/soapy.dll",
|
|
||||||
"RTLTCPSource": "./modules/rtl_tcp_source.dll"
|
|
||||||
}
|
|
@ -1,5 +0,0 @@
|
|||||||
{
|
|
||||||
"Radio 1": {
|
|
||||||
"demodulator":1
|
|
||||||
}
|
|
||||||
}
|
|
BIN
root/res/icons/center_tuning.png
Normal file
After Width: | Height: | Size: 6.5 KiB |
Before Width: | Height: | Size: 1.8 KiB After Width: | Height: | Size: 1.4 KiB |
BIN
root/res/icons/muted.png
Normal file
After Width: | Height: | Size: 5.8 KiB |
BIN
root/res/icons/normal_tuning.png
Normal file
After Width: | Height: | Size: 2.7 KiB |
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.0 KiB |
Before Width: | Height: | Size: 1.7 KiB After Width: | Height: | Size: 1.3 KiB |
BIN
root/res/icons/unmuted.png
Normal file
After Width: | Height: | Size: 5.5 KiB |
@ -1,4 +0,0 @@
|
|||||||
{
|
|
||||||
"device": "",
|
|
||||||
"devices": {}
|
|
||||||
}
|
|
@ -1,11 +1,18 @@
|
|||||||
{
|
{
|
||||||
|
"bandColors": {
|
||||||
|
"amateur": "#FF0000FF",
|
||||||
|
"aviation": "#00FF00FF",
|
||||||
|
"broadcast": "#0000FFFF",
|
||||||
|
"marine": "#00FFFFFF",
|
||||||
|
"military": "#FFFF00FF"
|
||||||
|
},
|
||||||
"bandPlan": "General",
|
"bandPlan": "General",
|
||||||
"bandPlanEnabled": true,
|
"bandPlanEnabled": true,
|
||||||
"centerTuning": false,
|
"centerTuning": false,
|
||||||
"fftHeight": 300,
|
"fftHeight": 300,
|
||||||
"frequency": 7350000,
|
"frequency": 105000000,
|
||||||
"max": -25.0,
|
"max": 0.0,
|
||||||
"maximized": true,
|
"maximized": false,
|
||||||
"menuOrder": [
|
"menuOrder": [
|
||||||
"Source",
|
"Source",
|
||||||
"Radio",
|
"Radio",
|
||||||
@ -17,7 +24,7 @@
|
|||||||
"Display"
|
"Display"
|
||||||
],
|
],
|
||||||
"menuWidth": 300,
|
"menuWidth": 300,
|
||||||
"min": -63.235294342041016,
|
"min": -70.0,
|
||||||
"moduleInstances": {
|
"moduleInstances": {
|
||||||
"AirspyHF+ Source": "airspyhf_source",
|
"AirspyHF+ Source": "airspyhf_source",
|
||||||
"Audio Sink": "audio_sink",
|
"Audio Sink": "audio_sink",
|
||||||
@ -25,7 +32,8 @@
|
|||||||
"RTL-TCP Source": "rtl_tcp_source",
|
"RTL-TCP Source": "rtl_tcp_source",
|
||||||
"Radio": "radio",
|
"Radio": "radio",
|
||||||
"Recorder": "recorder",
|
"Recorder": "recorder",
|
||||||
"SoapySDR Source": "soapy_source"
|
"SoapySDR Source": "soapy_source",
|
||||||
|
"SpyServer Source": "spyserver_source"
|
||||||
},
|
},
|
||||||
"modules": [
|
"modules": [
|
||||||
"./radio/Release/radio.dll",
|
"./radio/Release/radio.dll",
|
||||||
@ -34,26 +42,17 @@
|
|||||||
"./airspyhf_source/Release/airspyhf_source.dll",
|
"./airspyhf_source/Release/airspyhf_source.dll",
|
||||||
"./rtl_tcp_source/Release/rtl_tcp_source.dll",
|
"./rtl_tcp_source/Release/rtl_tcp_source.dll",
|
||||||
"./audio_sink/Release/audio_sink.dll",
|
"./audio_sink/Release/audio_sink.dll",
|
||||||
"./plutosdr_source/Release/plutosdr_source.dll"
|
"./plutosdr_source/Release/plutosdr_source.dll",
|
||||||
|
"./spyserver_source/Release/spyserver_source.dll"
|
||||||
],
|
],
|
||||||
"offset": 0.0,
|
"offset": 0.0,
|
||||||
"showWaterfall": true,
|
"showWaterfall": true,
|
||||||
"source": "Airspy HF+",
|
"source": "SoapySDR",
|
||||||
"streams": {
|
"streams": {
|
||||||
"Radio": {
|
"Radio": {
|
||||||
"muted": false,
|
"muted": false,
|
||||||
"sink": "Audio",
|
"sink": "Audio",
|
||||||
"volume": 0.13265305757522583
|
"volume": 0.5867347121238708
|
||||||
},
|
|
||||||
"Radio 1": {
|
|
||||||
"muted": false,
|
|
||||||
"sink": "Audio",
|
|
||||||
"volume": 0.6377550959587097
|
|
||||||
},
|
|
||||||
"Radio 2": {
|
|
||||||
"muted": false,
|
|
||||||
"sink": "Audio",
|
|
||||||
"volume": 0.4292035400867462
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"windowSize": {
|
"windowSize": {
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"IP": "192.168.2.1",
|
"IP": "192.168.2.1",
|
||||||
"gain": 0.0,
|
"gain": 0.0,
|
||||||
"gainMode": 2,
|
"gainMode": 0,
|
||||||
"sampleRate": 4000000.0
|
"sampleRate": 4000000.0
|
||||||
}
|
}
|
@ -1,44 +1,5 @@
|
|||||||
{
|
{
|
||||||
"Radio": {
|
"Radio": {
|
||||||
"AM": {
|
|
||||||
"bandwidth": 12500.0,
|
|
||||||
"snapInterval": 1000.0,
|
|
||||||
"squelchLevel": -100.0
|
|
||||||
},
|
|
||||||
"CW": {
|
|
||||||
"bandwidth": 200.0,
|
|
||||||
"snapInterval": 10.0,
|
|
||||||
"squelchLevel": -100.0
|
|
||||||
},
|
|
||||||
"DSB": {
|
|
||||||
"bandwidth": 6000.0,
|
|
||||||
"snapInterval": 100.0
|
|
||||||
},
|
|
||||||
"FM": {
|
|
||||||
"bandwidth": 12500.0,
|
|
||||||
"snapInterval": 10000.0,
|
|
||||||
"squelchLevel": -47.474998474121094
|
|
||||||
},
|
|
||||||
"LSB": {
|
|
||||||
"bandwidth": 3000.0,
|
|
||||||
"snapInterval": 100.0
|
|
||||||
},
|
|
||||||
"RAW": {
|
|
||||||
"snapInterval": 10000.0
|
|
||||||
},
|
|
||||||
"USB": {
|
|
||||||
"bandwidth": 3000.0,
|
|
||||||
"snapInterval": 100.0
|
|
||||||
},
|
|
||||||
"WFM": {
|
|
||||||
"bandwidth": 200000.0,
|
|
||||||
"deempMode": 0,
|
|
||||||
"snapInterval": 100000.0,
|
|
||||||
"squelchLevel": -100.0
|
|
||||||
},
|
|
||||||
"selectedDemodId": 2
|
|
||||||
},
|
|
||||||
"Radio 1": {
|
|
||||||
"AM": {
|
"AM": {
|
||||||
"bandwidth": 12500.0,
|
"bandwidth": 12500.0,
|
||||||
"snapInterval": 1000.0
|
"snapInterval": 1000.0
|
||||||
@ -70,43 +31,7 @@
|
|||||||
"bandwidth": 200000.0,
|
"bandwidth": 200000.0,
|
||||||
"deempMode": 0,
|
"deempMode": 0,
|
||||||
"snapInterval": 100000.0,
|
"snapInterval": 100000.0,
|
||||||
"squelchLevel": -100.0
|
"squelchLevel": -60.60599899291992
|
||||||
},
|
|
||||||
"selectedDemodId": 1
|
|
||||||
},
|
|
||||||
"Radio 2": {
|
|
||||||
"AM": {
|
|
||||||
"bandwidth": 12500.0,
|
|
||||||
"snapInterval": 1000.0
|
|
||||||
},
|
|
||||||
"CW": {
|
|
||||||
"bandwidth": 200.0,
|
|
||||||
"snapInterval": 10.0
|
|
||||||
},
|
|
||||||
"DSB": {
|
|
||||||
"bandwidth": 6000.0,
|
|
||||||
"snapInterval": 100.0
|
|
||||||
},
|
|
||||||
"FM": {
|
|
||||||
"bandwidth": 12500.0,
|
|
||||||
"snapInterval": 10000.0
|
|
||||||
},
|
|
||||||
"LSB": {
|
|
||||||
"bandwidth": 3000.0,
|
|
||||||
"snapInterval": 100.0
|
|
||||||
},
|
|
||||||
"RAW": {
|
|
||||||
"snapInterval": 10000.0
|
|
||||||
},
|
|
||||||
"USB": {
|
|
||||||
"bandwidth": 3000.0,
|
|
||||||
"snapInterval": 100.0
|
|
||||||
},
|
|
||||||
"WFM": {
|
|
||||||
"bandwidth": 200000.0,
|
|
||||||
"deempMode": 1,
|
|
||||||
"snapInterval": 100000.0,
|
|
||||||
"squelchLevel": -70.2020034790039
|
|
||||||
},
|
},
|
||||||
"selectedDemodId": 1
|
"selectedDemodId": 1
|
||||||
}
|
}
|
||||||
|
@ -1,49 +1,12 @@
|
|||||||
{
|
{
|
||||||
"device": "AirSpy HF+ [c852435de0224af7]",
|
"device": "Generic RTL2832U OEM :: 00000001",
|
||||||
"devices": {
|
"devices": {
|
||||||
"": {
|
"Generic RTL2832U OEM :: 00000001": {
|
||||||
"agc": true,
|
"agc": true,
|
||||||
"gains": {
|
"gains": {
|
||||||
"PGA": 0.0
|
"TUNER": 0.0
|
||||||
},
|
},
|
||||||
"sampleRate": 4000000.0
|
"sampleRate": 2560000.0
|
||||||
},
|
|
||||||
"AirSpy HF+ [c852435de0224af7]": {
|
|
||||||
"agc": false,
|
|
||||||
"gains": {
|
|
||||||
"LNA": 6.0,
|
|
||||||
"RF": -48.0
|
|
||||||
},
|
|
||||||
"sampleRate": 768000.0
|
|
||||||
},
|
|
||||||
"CABLE Output (VB-Audio Virtual Cable)": {
|
|
||||||
"sampleRate": 96000.0
|
|
||||||
},
|
|
||||||
"Default Device": {
|
|
||||||
"agc": false,
|
|
||||||
"sampleRate": 192000.0
|
|
||||||
},
|
|
||||||
"Generic RTL2832U OEM :: 00000001": {
|
|
||||||
"agc": false,
|
|
||||||
"gains": {
|
|
||||||
"TUNER": 37.3390007019043
|
|
||||||
},
|
|
||||||
"sampleRate": 250000.0
|
|
||||||
},
|
|
||||||
"HackRF One #0 901868dc282c8f8b": {
|
|
||||||
"gains": {
|
|
||||||
"AMP": 0.0,
|
|
||||||
"LNA": 24.503000259399414,
|
|
||||||
"VGA": 16.332000732421875
|
|
||||||
},
|
|
||||||
"sampleRate": 8000000.0
|
|
||||||
},
|
|
||||||
"Microphone (Realtek High Definition Audio)": {
|
|
||||||
"agc": false,
|
|
||||||
"sampleRate": 44100.0
|
|
||||||
},
|
|
||||||
"PulseAudio": {
|
|
||||||
"sampleRate": 96000.0
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
7
sdrpp_0.2.5_beta_airspyhf/band_colors.json
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
{
|
||||||
|
"broadcast": "#0000FFFF",
|
||||||
|
"amateur": "#FF0000FF",
|
||||||
|
"aviation": "#00FF00FF",
|
||||||
|
"marine": "#00FFFFFF",
|
||||||
|
"military": "#FFFF00FF"
|
||||||
|
}
|
267
sdrpp_0.2.5_beta_airspyhf/bandplans/general.json
Normal file
@ -0,0 +1,267 @@
|
|||||||
|
{
|
||||||
|
"name": "General",
|
||||||
|
"country_name": "Worldwide",
|
||||||
|
"country_code": "--",
|
||||||
|
"author_name": "Ryzerth",
|
||||||
|
"author_url": "https://github.com/AlexandreRouma",
|
||||||
|
"bands": [
|
||||||
|
{
|
||||||
|
"name": "Long Wave",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 148500,
|
||||||
|
"end": 283500
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Medium Wave",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 526500,
|
||||||
|
"end": 1606500
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 2300000,
|
||||||
|
"end": 2468000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 3200000,
|
||||||
|
"end": 3400000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 3950000,
|
||||||
|
"end": 4000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 4750000,
|
||||||
|
"end": 4995000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 5005000,
|
||||||
|
"end": 5060000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 5900000,
|
||||||
|
"end": 6200000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 7200000,
|
||||||
|
"end": 7450000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 9400000,
|
||||||
|
"end": 9900000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 11600000,
|
||||||
|
"end": 12100000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 13570000,
|
||||||
|
"end": 13870000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 15100000,
|
||||||
|
"end": 15800000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 17480000,
|
||||||
|
"end": 17900000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 18900000,
|
||||||
|
"end": 19020000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 21450000,
|
||||||
|
"end": 21850000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Shortwave Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 25670000,
|
||||||
|
"end": 26100000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "FM Broadcast",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 87500000,
|
||||||
|
"end": 108000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Air Band VOR/ILS",
|
||||||
|
"type": "aviation",
|
||||||
|
"start": 108000000,
|
||||||
|
"end": 118000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Air Band Voice",
|
||||||
|
"type": "aviation",
|
||||||
|
"start": 118000000,
|
||||||
|
"end": 137000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "160m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1800000,
|
||||||
|
"end": 2000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3500000,
|
||||||
|
"end": 3950000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "60m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 5351500,
|
||||||
|
"end": 5366500
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7000000,
|
||||||
|
"end": 7200000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "30m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 10100000,
|
||||||
|
"end": 10150000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "20m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 14000000,
|
||||||
|
"end": 14350000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "17m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 18068000,
|
||||||
|
"end": 18168000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "15m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 21000000,
|
||||||
|
"end": 21450000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "12m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 24890000,
|
||||||
|
"end": 24990000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "CB",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 26960000,
|
||||||
|
"end": 27410000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "10m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 28000000,
|
||||||
|
"end": 29750000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "6m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 50000000,
|
||||||
|
"end": 54000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "2m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 144000000,
|
||||||
|
"end": 148000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Marine",
|
||||||
|
"type": "marine",
|
||||||
|
"start": 156000000,
|
||||||
|
"end": 162025000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "1.25m Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 222000000,
|
||||||
|
"end": 225000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Military Air",
|
||||||
|
"type": "military",
|
||||||
|
"start": 225000000,
|
||||||
|
"end": 380000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Military Sat",
|
||||||
|
"type": "military",
|
||||||
|
"start": 240000000,
|
||||||
|
"end": 270000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "70cm Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 420000000,
|
||||||
|
"end": 450000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "PMR446",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 446000000,
|
||||||
|
"end": 446200000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "33cm Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 902000000,
|
||||||
|
"end": 928000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "23cm Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1240000000,
|
||||||
|
"end": 1300000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "13cm Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 2300000000,
|
||||||
|
"end": 2310000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "13cm Ham Band",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 2390000000,
|
||||||
|
"end": 2450000000
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
141
sdrpp_0.2.5_beta_airspyhf/bandplans/germany.json
Normal file
@ -0,0 +1,141 @@
|
|||||||
|
{
|
||||||
|
"name": "Germany",
|
||||||
|
"country_name": "Germany",
|
||||||
|
"country_code": "DE",
|
||||||
|
"author_name": "Tobias Mädel",
|
||||||
|
"author_url": "https://tbspace.de",
|
||||||
|
"bands": [
|
||||||
|
{
|
||||||
|
"name": "LW",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 135700,
|
||||||
|
"end": 137800
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "630m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 472000,
|
||||||
|
"end": 479000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "160m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1810000,
|
||||||
|
"end": 2000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3500000,
|
||||||
|
"end": 3800000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "60m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 5351500,
|
||||||
|
"end": 5366500
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7000000,
|
||||||
|
"end": 7200000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "30m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 10100000,
|
||||||
|
"end": 10150000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "20m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 14000000,
|
||||||
|
"end": 14350000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "17m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 18068000,
|
||||||
|
"end": 18168000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "15m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 21000000,
|
||||||
|
"end": 21450000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "12m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 24890000,
|
||||||
|
"end": 24990000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "CB",
|
||||||
|
"type": "other",
|
||||||
|
"start": 26565000,
|
||||||
|
"end": 27405000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "10m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 28000000,
|
||||||
|
"end": 29700000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "6m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 50030000,
|
||||||
|
"end": 51000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "4m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 70150000,
|
||||||
|
"end": 70200000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "FM",
|
||||||
|
"type": "broadcast",
|
||||||
|
"start": 87500000,
|
||||||
|
"end": 108000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "2m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 144000000,
|
||||||
|
"end": 146000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Freenet",
|
||||||
|
"type": "other",
|
||||||
|
"start": 149025000,
|
||||||
|
"end": 149115625
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "70cm",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 430000000,
|
||||||
|
"end": 440000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "PMR446",
|
||||||
|
"type": "other",
|
||||||
|
"start": 446006250,
|
||||||
|
"end": 446196875
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "23cm",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1240000000,
|
||||||
|
"end": 1300000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "13cm",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 2320000000,
|
||||||
|
"end": 2450000000
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
135
sdrpp_0.2.5_beta_airspyhf/bandplans/russia.json
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
{
|
||||||
|
"name": "Russia",
|
||||||
|
"country_name": "Russia",
|
||||||
|
"country_code": "RU",
|
||||||
|
"author_name": "Raov",
|
||||||
|
"author_url": "https://twitter.com/raov_birbtog",
|
||||||
|
"bands": [
|
||||||
|
{
|
||||||
|
"name": "160m CW",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1810000,
|
||||||
|
"end": 1838000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "160m NB",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1838000,
|
||||||
|
"end": 1840000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "160m + Digi",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1840000,
|
||||||
|
"end": 1843000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "160m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 1843000,
|
||||||
|
"end": 2000000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m CW",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3500000,
|
||||||
|
"end": 3510000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m CW Contest",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3510000,
|
||||||
|
"end": 3560000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m CW",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3560000,
|
||||||
|
"end": 3570000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m NB, Digi 200Hz",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3570000,
|
||||||
|
"end": 3580000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m NB, Digi 500Hz",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3580000,
|
||||||
|
"end": 3600000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m SSB Contest",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3600000,
|
||||||
|
"end": 3650000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3650000,
|
||||||
|
"end": 3700000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "80m SSB Contest",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 3700000,
|
||||||
|
"end": 3800000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "60m CW 200Hz",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 5351500,
|
||||||
|
"end": 5354000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "60m USB",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 5354000,
|
||||||
|
"end": 5366000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "60m CW 20Hz",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 5356000,
|
||||||
|
"end": 5366500
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m CW",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7000000,
|
||||||
|
"end": 7040000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m NB, Digi 500Hz",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7040000,
|
||||||
|
"end": 7050000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7050000,
|
||||||
|
"end": 7060000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m SSB Contest",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7060000,
|
||||||
|
"end": 7100000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7100000,
|
||||||
|
"end": 7130000
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "40m SSB Contest",
|
||||||
|
"type": "amateur",
|
||||||
|
"start": 7130000,
|
||||||
|
"end": 7200000
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
46
sdrpp_0.2.5_beta_airspyhf/config.json
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
{
|
||||||
|
"bandColors": {
|
||||||
|
"amateur": "#FF0000FF",
|
||||||
|
"aviation": "#00FF00FF",
|
||||||
|
"broadcast": "#0000FFFF",
|
||||||
|
"marine": "#00FFFFFF",
|
||||||
|
"military": "#FFFF00FF"
|
||||||
|
},
|
||||||
|
"bandPlan": "General",
|
||||||
|
"bandPlanEnabled": true,
|
||||||
|
"centerTuning": false,
|
||||||
|
"fftHeight": 300,
|
||||||
|
"frequency": 100004000,
|
||||||
|
"max": 0.0,
|
||||||
|
"maximized": false,
|
||||||
|
"menuOrder": [
|
||||||
|
"Source",
|
||||||
|
"Radio",
|
||||||
|
"Recorder",
|
||||||
|
"Sinks",
|
||||||
|
"Audio",
|
||||||
|
"Scripting",
|
||||||
|
"Band Plan",
|
||||||
|
"Display"
|
||||||
|
],
|
||||||
|
"menuWidth": 300,
|
||||||
|
"min": -70.0,
|
||||||
|
"moduleInstances": {
|
||||||
|
"AirspyHF+ Source": "airspyhf_source",
|
||||||
|
"Audio Sink": "audio_sink",
|
||||||
|
"PlutoSDR Source": "plutosdr_source",
|
||||||
|
"RTL-TCP Source": "rtl_tcp_source",
|
||||||
|
"Radio": "radio",
|
||||||
|
"Recorder": "recorder",
|
||||||
|
"SoapySDR Source": "soapy_source"
|
||||||
|
},
|
||||||
|
"modules": [],
|
||||||
|
"offset": 0.0,
|
||||||
|
"showWaterfall": true,
|
||||||
|
"source": "",
|
||||||
|
"streams": {},
|
||||||
|
"windowSize": {
|
||||||
|
"h": 720,
|
||||||
|
"w": 1280
|
||||||
|
}
|
||||||
|
}
|
0
sdrpp_0.2.5_beta_airspyhf/modules/.gitkeep
Normal file
0
sdrpp_0.2.5_beta_airspyhf/recordings/.gitkeep
Normal file
BIN
sdrpp_0.2.5_beta_airspyhf/res/fonts/Roboto-Medium.ttf
Normal file
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/center_tuning.png
Normal file
After Width: | Height: | Size: 6.5 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/menu.png
Normal file
After Width: | Height: | Size: 1.4 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/muted.png
Normal file
After Width: | Height: | Size: 5.8 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/normal_tuning.png
Normal file
After Width: | Height: | Size: 2.7 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/play.png
Normal file
After Width: | Height: | Size: 2.0 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/sdrpp.ico
Normal file
After Width: | Height: | Size: 33 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/sdrpp.png
Normal file
After Width: | Height: | Size: 21 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/stop.png
Normal file
After Width: | Height: | Size: 1.3 KiB |
BIN
sdrpp_0.2.5_beta_airspyhf/res/icons/unmuted.png
Normal file
After Width: | Height: | Size: 5.5 KiB |
@ -8,6 +8,7 @@
|
|||||||
#include <SoapySDR/Logger.hpp>
|
#include <SoapySDR/Logger.hpp>
|
||||||
#include <core.h>
|
#include <core.h>
|
||||||
#include <gui/style.h>
|
#include <gui/style.h>
|
||||||
|
#include <options.h>
|
||||||
|
|
||||||
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
||||||
|
|
||||||
@ -386,7 +387,7 @@ private:
|
|||||||
};
|
};
|
||||||
|
|
||||||
MOD_EXPORT void _INIT_() {
|
MOD_EXPORT void _INIT_() {
|
||||||
config.setPath(ROOT_DIR "/soapy_source_config.json");
|
config.setPath(options::opts.root + "/soapy_source_config.json");
|
||||||
json defConf;
|
json defConf;
|
||||||
defConf["device"] = "";
|
defConf["device"] = "";
|
||||||
defConf["devices"] = json({});
|
defConf["devices"] = json({});
|
||||||
|
20
spyserver_source/CMakeLists.txt
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
project(spyserver_source)
|
||||||
|
|
||||||
|
if (MSVC)
|
||||||
|
set(CMAKE_CXX_FLAGS "-O2 /std:c++17 /EHsc")
|
||||||
|
else()
|
||||||
|
set(CMAKE_CXX_FLAGS "-O3 -std=c++17 -fpermissive")
|
||||||
|
endif (MSVC)
|
||||||
|
|
||||||
|
include_directories("src/")
|
||||||
|
|
||||||
|
file(GLOB SRC "src/*.cpp")
|
||||||
|
|
||||||
|
add_library(spyserver_source SHARED ${SRC})
|
||||||
|
target_link_libraries(spyserver_source PRIVATE sdrpp_core)
|
||||||
|
set_target_properties(spyserver_source PROPERTIES PREFIX "")
|
||||||
|
|
||||||
|
if(WIN32)
|
||||||
|
target_link_libraries(spyserver_source PRIVATE wsock32 ws2_32)
|
||||||
|
endif()
|
178
spyserver_source/src/main.cpp
Normal file
@ -0,0 +1,178 @@
|
|||||||
|
#include <spyserver_client.h>
|
||||||
|
#include <imgui.h>
|
||||||
|
#include <spdlog/spdlog.h>
|
||||||
|
#include <new_module.h>
|
||||||
|
#include <gui/gui.h>
|
||||||
|
#include <signal_path/signal_path.h>
|
||||||
|
#include <core.h>
|
||||||
|
#include <gui/style.h>
|
||||||
|
|
||||||
|
#define CONCAT(a, b) ((std::string(a) + b).c_str())
|
||||||
|
|
||||||
|
SDRPP_MOD_INFO {
|
||||||
|
/* Name: */ "spyserver_source",
|
||||||
|
/* Description: */ "SpyServer source module for SDR++",
|
||||||
|
/* Author: */ "Ryzerth",
|
||||||
|
/* Version: */ 0, 1, 0,
|
||||||
|
/* Max instances */ 1
|
||||||
|
};
|
||||||
|
|
||||||
|
class SpyServerSourceModule : public ModuleManager::Instance {
|
||||||
|
public:
|
||||||
|
SpyServerSourceModule(std::string name) {
|
||||||
|
this->name = name;
|
||||||
|
|
||||||
|
sampleRate = 2560000.0;
|
||||||
|
|
||||||
|
handler.ctx = this;
|
||||||
|
handler.selectHandler = menuSelected;
|
||||||
|
handler.deselectHandler = menuDeselected;
|
||||||
|
handler.menuHandler = menuHandler;
|
||||||
|
handler.startHandler = start;
|
||||||
|
handler.stopHandler = stop;
|
||||||
|
handler.tuneHandler = tune;
|
||||||
|
handler.stream = &client.iqStream;
|
||||||
|
sigpath::sourceManager.registerSource("SpyServer", &handler);
|
||||||
|
}
|
||||||
|
|
||||||
|
~SpyServerSourceModule() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void enable() {
|
||||||
|
enabled = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void disable() {
|
||||||
|
enabled = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool isEnabled() {
|
||||||
|
return enabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
static void menuSelected(void* ctx) {
|
||||||
|
SpyServerSourceModule* _this = (SpyServerSourceModule*)ctx;
|
||||||
|
core::setInputSampleRate(_this->sampleRate);
|
||||||
|
spdlog::info("SpyServerSourceModule '{0}': Menu Select!", _this->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void menuDeselected(void* ctx) {
|
||||||
|
SpyServerSourceModule* _this = (SpyServerSourceModule*)ctx;
|
||||||
|
spdlog::info("SpyServerSourceModule '{0}': Menu Deselect!", _this->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void start(void* ctx) {
|
||||||
|
SpyServerSourceModule* _this = (SpyServerSourceModule*)ctx;
|
||||||
|
if (_this->running) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!_this->client.connectToSpyserver(_this->ip, _this->port)) {
|
||||||
|
spdlog::error("Could not connect to {0}:{1}", _this->ip, _this->port);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
_this->client.tune(_this->freq);
|
||||||
|
_this->client.setSampleRate(_this->sampleRate);
|
||||||
|
//_this->client.setGainIndex(_this->gain);
|
||||||
|
//_this->client.setGainMode(!_this->tunerAGC);
|
||||||
|
//_this->client.setDirectSampling(_this->directSamplingMode);
|
||||||
|
//_this->client.setAGCMode(_this->rtlAGC);
|
||||||
|
_this->running = true;
|
||||||
|
spdlog::info("SpyServerSourceModule '{0}': Start!", _this->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void stop(void* ctx) {
|
||||||
|
SpyServerSourceModule* _this = (SpyServerSourceModule*)ctx;
|
||||||
|
if (!_this->running) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
_this->running = false;
|
||||||
|
_this->client.disconnect();
|
||||||
|
spdlog::info("SpyServerSourceModule '{0}': Stop!", _this->name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tune(double freq, void* ctx) {
|
||||||
|
SpyServerSourceModule* _this = (SpyServerSourceModule*)ctx;
|
||||||
|
if (_this->running) {
|
||||||
|
_this->client.tune(freq);
|
||||||
|
}
|
||||||
|
_this->freq = freq;
|
||||||
|
spdlog::info("SpyServerSourceModule '{0}': Tune: {1}!", _this->name, freq);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void menuHandler(void* ctx) {
|
||||||
|
SpyServerSourceModule* _this = (SpyServerSourceModule*)ctx;
|
||||||
|
float menuWidth = ImGui::GetContentRegionAvailWidth();
|
||||||
|
float portWidth = ImGui::CalcTextSize("00000").x + 20;
|
||||||
|
|
||||||
|
ImGui::SetNextItemWidth(menuWidth - portWidth);
|
||||||
|
ImGui::InputText(CONCAT("##_ip_select_", _this->name), _this->ip, 1024);
|
||||||
|
ImGui::SameLine();
|
||||||
|
ImGui::SetNextItemWidth(portWidth);
|
||||||
|
ImGui::InputInt(CONCAT("##_port_select_", _this->name), &_this->port, 0);
|
||||||
|
|
||||||
|
ImGui::SetNextItemWidth(ImGui::CalcTextSize("OOOOOOOOOO").x);
|
||||||
|
if (ImGui::Combo("Direct sampling", &_this->directSamplingMode, "Disabled\0I branch\0Q branch\0")) {
|
||||||
|
if (_this->running) {
|
||||||
|
//_this->client.setDirectSampling(_this->directSamplingMode);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ImGui::Checkbox("RTL AGC", &_this->rtlAGC)) {
|
||||||
|
if (_this->running) {
|
||||||
|
//_this->client.setAGCMode(_this->rtlAGC);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ImGui::Checkbox("Tuner AGC", &_this->tunerAGC)) {
|
||||||
|
if (_this->running) {
|
||||||
|
//_this->client.setGainMode(!_this->tunerAGC);
|
||||||
|
if (!_this->tunerAGC) {
|
||||||
|
//_this->client.setGainIndex(_this->gain);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_this->tunerAGC) { style::beginDisabled(); }
|
||||||
|
ImGui::SetNextItemWidth(menuWidth);
|
||||||
|
if (ImGui::SliderInt(CONCAT("##_gain_select_", _this->name), &_this->gain, 0, 29, "")) {
|
||||||
|
if (_this->running) {
|
||||||
|
//_this->client.setGainIndex(_this->gain);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (_this->tunerAGC) { style::endDisabled(); }
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string name;
|
||||||
|
bool enabled = true;
|
||||||
|
dsp::stream<dsp::complex_t> stream;
|
||||||
|
double sampleRate;
|
||||||
|
SourceManager::SourceHandler handler;
|
||||||
|
std::thread workerThread;
|
||||||
|
SpyServerClient client;
|
||||||
|
bool running = false;
|
||||||
|
double freq;
|
||||||
|
char ip[1024] = "localhost";
|
||||||
|
int port = 5555;
|
||||||
|
int gain = 0;
|
||||||
|
bool rtlAGC = false;
|
||||||
|
bool tunerAGC = false;
|
||||||
|
int directSamplingMode = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
MOD_EXPORT void _INIT_() {
|
||||||
|
// Do your one time init here
|
||||||
|
}
|
||||||
|
|
||||||
|
MOD_EXPORT ModuleManager::Instance* _CREATE_INSTANCE_(std::string name) {
|
||||||
|
return new SpyServerSourceModule(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
MOD_EXPORT void _DELETE_INSTANCE_(ModuleManager::Instance* instance) {
|
||||||
|
delete (SpyServerSourceModule*)instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
MOD_EXPORT void _END_() {
|
||||||
|
// Do your one shutdown here
|
||||||
|
}
|
254
spyserver_source/src/spyserver_client.cpp
Normal file
@ -0,0 +1,254 @@
|
|||||||
|
#include <spyserver_client.h>
|
||||||
|
#include <spdlog/spdlog.h>
|
||||||
|
|
||||||
|
SpyServerClient::SpyServerClient() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
bool SpyServerClient::connectToSpyserver(char* host, int port) {
|
||||||
|
if (connected) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
struct addrinfo *result = NULL;
|
||||||
|
struct addrinfo *ptr = NULL;
|
||||||
|
struct addrinfo hints;
|
||||||
|
|
||||||
|
ZeroMemory( &hints, sizeof(hints) );
|
||||||
|
hints.ai_family = AF_UNSPEC;
|
||||||
|
hints.ai_socktype = SOCK_STREAM;
|
||||||
|
hints.ai_protocol = IPPROTO_TCP;
|
||||||
|
|
||||||
|
char buf[128];
|
||||||
|
sprintf(buf, "%hu", port);
|
||||||
|
|
||||||
|
int iResult = getaddrinfo(host, buf, &hints, &result);
|
||||||
|
if (iResult != 0) {
|
||||||
|
// TODO: log error
|
||||||
|
printf("A");
|
||||||
|
WSACleanup();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
ptr = result;
|
||||||
|
|
||||||
|
sock = socket(ptr->ai_family, ptr->ai_socktype, ptr->ai_protocol);
|
||||||
|
|
||||||
|
if (sock == INVALID_SOCKET) {
|
||||||
|
// TODO: log error
|
||||||
|
printf("B");
|
||||||
|
freeaddrinfo(result);
|
||||||
|
WSACleanup();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
iResult = connect(sock, ptr->ai_addr, (int)ptr->ai_addrlen);
|
||||||
|
if (iResult == SOCKET_ERROR) {
|
||||||
|
printf("C");
|
||||||
|
closesocket(sock);
|
||||||
|
freeaddrinfo(result);
|
||||||
|
WSACleanup();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
freeaddrinfo(result);
|
||||||
|
#else
|
||||||
|
sockfd = socket(AF_INET, SOCK_STREAM, 0);
|
||||||
|
if (sockfd < 0) {
|
||||||
|
// TODO: Log error
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
struct hostent *server = gethostbyname(host);
|
||||||
|
struct sockaddr_in serv_addr;
|
||||||
|
bzero(&serv_addr, sizeof(struct sockaddr_in));
|
||||||
|
serv_addr.sin_family = AF_INET;
|
||||||
|
bcopy((char *)server->h_addr, (char *)&serv_addr.sin_addr.s_addr, server->h_length);
|
||||||
|
serv_addr.sin_port = htons(port);
|
||||||
|
if (connect(sockfd,(struct sockaddr *)&serv_addr,sizeof(serv_addr)) < 0) {
|
||||||
|
// TODO: log error
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Switch to non-blocking mode
|
||||||
|
#ifdef _WIN32
|
||||||
|
unsigned long mode = 1;
|
||||||
|
ioctlsocket(sock, FIONBIO, &mode);
|
||||||
|
#else
|
||||||
|
fcntl(sockfd, F_SETFL, fcntl(sockfd, F_GETFL, 0) | O_NONBLOCK)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
connected = true;
|
||||||
|
waiting = true;
|
||||||
|
|
||||||
|
workerThread = std::thread(&SpyServerClient::worker, this);
|
||||||
|
|
||||||
|
printf("Connected");
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool SpyServerClient::disconnect() {
|
||||||
|
if (!connected) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
waiting = false;
|
||||||
|
if (workerThread.joinable()) {
|
||||||
|
workerThread.join();
|
||||||
|
}
|
||||||
|
#ifdef _WIN32
|
||||||
|
closesocket(sock);
|
||||||
|
WSACleanup();
|
||||||
|
#else
|
||||||
|
close(sockfd);
|
||||||
|
#endif
|
||||||
|
connected = false;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SpyServerClient::setSampleRate(uint32_t setSampleRate) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void SpyServerClient::tune(uint32_t freq) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
int SpyServerClient::receive(char* buf, int count) {
|
||||||
|
#ifdef _WIN32
|
||||||
|
return checkError(recv(sock, (char*)buf, count, 0), count);
|
||||||
|
#else
|
||||||
|
return checkError(read(sockfd, buf, count));
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
int SpyServerClient::checkError(int len, int expected) {
|
||||||
|
#ifdef _WIN32
|
||||||
|
if (len != SOCKET_ERROR) { return len; }
|
||||||
|
int code = WSAGetLastError();
|
||||||
|
if (code == WSAEWOULDBLOCK) { return 0; }
|
||||||
|
spdlog::error("{0}", code);
|
||||||
|
return -1;
|
||||||
|
#else
|
||||||
|
if (len <= expected) {
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
if (len == EAGAIN || len == EWOULDBLOCK) { return 0; }
|
||||||
|
return -1;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
int SpyServerClient::receiveSync(char* buf, int count) {
|
||||||
|
int len = receive(buf, count);
|
||||||
|
while (len == 0 && waiting) {
|
||||||
|
len = receive(buf, count);
|
||||||
|
}
|
||||||
|
if (!waiting) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SpyServerClient::worker() {
|
||||||
|
// Allocate dummy buffer
|
||||||
|
char* dummyBuf = (char*)malloc(1000000);
|
||||||
|
|
||||||
|
// Send hello
|
||||||
|
hello();
|
||||||
|
|
||||||
|
// SETTING_STREAMING_MODE = 0,
|
||||||
|
// SETTING_STREAMING_ENABLED = 1,
|
||||||
|
// SETTING_GAIN = 2,
|
||||||
|
|
||||||
|
// SETTING_IQ_FORMAT = 100, // 0x64
|
||||||
|
// SETTING_IQ_FREQUENCY = 101, // 0x65
|
||||||
|
// SETTING_IQ_DECIMATION = 102, // 0x66
|
||||||
|
// SETTING_IQ_DIGITAL_GAIN = 103, // 0x67
|
||||||
|
|
||||||
|
// Set settings
|
||||||
|
setSetting(SETTING_STREAMING_MODE, STREAM_MODE_IQ_ONLY);
|
||||||
|
setSetting(SETTING_GAIN, 5);
|
||||||
|
setSetting(SETTING_IQ_FORMAT, STREAM_FORMAT_FLOAT);
|
||||||
|
setSetting(SETTING_IQ_FREQUENCY, 2000000);
|
||||||
|
setSetting(SETTING_IQ_DECIMATION, 1);
|
||||||
|
setSetting(SETTING_IQ_DIGITAL_GAIN, 1);
|
||||||
|
|
||||||
|
// Enable stream
|
||||||
|
setSetting(SETTING_STREAMING_ENABLED, 1);
|
||||||
|
|
||||||
|
// Main message receive loop
|
||||||
|
while (true) {
|
||||||
|
MessageHeader msgHeader;
|
||||||
|
int len = receiveSync((char*)&msgHeader, sizeof(MessageHeader));
|
||||||
|
if (len < 0) {
|
||||||
|
spdlog::error("Socket error");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (len == 0) { return; }
|
||||||
|
|
||||||
|
int type = (msgHeader.MessageType & 0xFFFF);
|
||||||
|
|
||||||
|
if (type == MSG_TYPE_DEVICE_INFO) {
|
||||||
|
DeviceInfo devInfo;
|
||||||
|
len = receiveSync((char*)&devInfo, sizeof(DeviceInfo));
|
||||||
|
if (len < 0) {
|
||||||
|
spdlog::error("A Socket error");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (len == 0) { return; }
|
||||||
|
|
||||||
|
spdlog::warn("Dev type: {0}", devInfo.DeviceType);
|
||||||
|
}
|
||||||
|
// else if (type == MSG_TYPE_FLOAT_IQ) {
|
||||||
|
// //if (iqStream.aquire() < 0) { return; }
|
||||||
|
// len = receiveSync(dummyBuf, msgHeader.BodySize);
|
||||||
|
// //iqStream.write(msgHeader.BodySize);
|
||||||
|
// if (len < 0) {
|
||||||
|
// spdlog::error("T Socket error");
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
|
// if (len == 0) { return; }
|
||||||
|
// }
|
||||||
|
else if (msgHeader.BodySize > 0) {
|
||||||
|
len = receiveSync(dummyBuf, msgHeader.BodySize);
|
||||||
|
if (len < 0) {
|
||||||
|
spdlog::error("B Socket error {0}", msgHeader.ProtocolID);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (len == 0) { return; }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
free(dummyBuf);
|
||||||
|
}
|
||||||
|
|
||||||
|
void SpyServerClient::sendCommand(uint32_t cmd, void* body, size_t bodySize) {
|
||||||
|
int size = sizeof(CommandHeader) + bodySize;
|
||||||
|
char* buf = new char[size];
|
||||||
|
CommandHeader* cmdHdr = (CommandHeader*)buf;
|
||||||
|
memcpy(&buf[sizeof(CommandHeader)], body, bodySize);
|
||||||
|
cmdHdr->CommandType = cmd;
|
||||||
|
cmdHdr->BodySize = bodySize;
|
||||||
|
#ifdef _WIN32
|
||||||
|
send(sock, buf, size, 0);
|
||||||
|
#else
|
||||||
|
write(sockfd, buf, size);
|
||||||
|
#endif
|
||||||
|
delete[] buf;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SpyServerClient::setSetting(uint32_t setting, uint32_t value) {
|
||||||
|
char buf[sizeof(SettingTarget) + sizeof(uint32_t)];
|
||||||
|
SettingTarget* tgt = (SettingTarget*)buf;
|
||||||
|
uint32_t* val = (uint32_t*)&buf[sizeof(SettingTarget)];
|
||||||
|
tgt->SettingType = setting;
|
||||||
|
*val = value;
|
||||||
|
sendCommand(CMD_SET_SETTING, buf, sizeof(SettingTarget) + sizeof(uint32_t));
|
||||||
|
}
|
||||||
|
|
||||||
|
void SpyServerClient::hello() {
|
||||||
|
char buf[1024];
|
||||||
|
ClientHandshake* handshake = (ClientHandshake*)buf;
|
||||||
|
handshake->ProtocolVersion = SPYSERVER_PROTOCOL_VERSION;
|
||||||
|
strcpy(&buf[sizeof(ClientHandshake)], "sdr++");
|
||||||
|
sendCommand(CMD_HELLO, buf, sizeof(ClientHandshake) + 5);
|
||||||
|
}
|
69
spyserver_source/src/spyserver_client.h
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
#pragma once
|
||||||
|
#include <spyserver_protocol.h>
|
||||||
|
#include <dsp/stream.h>
|
||||||
|
#include <dsp/types.h>
|
||||||
|
#include <thread>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include <WinSock2.h>
|
||||||
|
#include <WS2tcpip.h>
|
||||||
|
#else
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <strings.h>
|
||||||
|
#include <sys/types.h>
|
||||||
|
#include <sys/socket.h>
|
||||||
|
#include <netinet/in.h>
|
||||||
|
#include <netdb.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#define __attribute__(x)
|
||||||
|
#pragma pack(push, 1)
|
||||||
|
#endif
|
||||||
|
struct command_t{
|
||||||
|
unsigned char cmd;
|
||||||
|
unsigned int param;
|
||||||
|
}__attribute__((packed));
|
||||||
|
#ifdef _WIN32
|
||||||
|
#pragma pack(pop)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
class SpyServerClient {
|
||||||
|
public:
|
||||||
|
SpyServerClient();
|
||||||
|
|
||||||
|
bool connectToSpyserver(char* host, int port);
|
||||||
|
bool disconnect();
|
||||||
|
|
||||||
|
void start();
|
||||||
|
void stop();
|
||||||
|
|
||||||
|
void setSampleRate(uint32_t setSampleRate);
|
||||||
|
|
||||||
|
void tune(uint32_t freq);
|
||||||
|
|
||||||
|
dsp::stream<dsp::complex_t> iqStream;
|
||||||
|
|
||||||
|
private:
|
||||||
|
int receive(char* buf, int count);
|
||||||
|
int receiveSync(char* buf, int count);
|
||||||
|
int checkError(int err, int expected);
|
||||||
|
void worker();
|
||||||
|
|
||||||
|
void sendCommand(uint32_t cmd, void* body, size_t bodySize);
|
||||||
|
void setSetting(uint32_t setting, uint32_t value);
|
||||||
|
|
||||||
|
void hello();
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
SOCKET sock;
|
||||||
|
#else
|
||||||
|
int sockfd;
|
||||||
|
#endif
|
||||||
|
bool connected = false;
|
||||||
|
bool waiting = false;
|
||||||
|
|
||||||
|
std::thread workerThread;
|
||||||
|
|
||||||
|
};
|
188
spyserver_source/src/spyserver_protocol.h
Normal file
@ -0,0 +1,188 @@
|
|||||||
|
/*
|
||||||
|
SPY Server protocol structures and constants
|
||||||
|
Copyright (C) 2017 Youssef Touil youssef@live.com
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <limits.h>
|
||||||
|
|
||||||
|
#define SPYSERVER_PROTOCOL_VERSION (((2) << 24) | ((0) << 16) | (1700))
|
||||||
|
|
||||||
|
#define SPYSERVER_MAX_COMMAND_BODY_SIZE (256)
|
||||||
|
#define SPYSERVER_MAX_MESSAGE_BODY_SIZE (1 << 20)
|
||||||
|
#define SPYSERVER_MAX_DISPLAY_PIXELS (1 << 15)
|
||||||
|
#define SPYSERVER_MIN_DISPLAY_PIXELS (100)
|
||||||
|
#define SPYSERVER_MAX_FFT_DB_RANGE (150)
|
||||||
|
#define SPYSERVER_MIN_FFT_DB_RANGE (10)
|
||||||
|
#define SPYSERVER_MAX_FFT_DB_OFFSET (100)
|
||||||
|
|
||||||
|
enum DeviceType
|
||||||
|
{
|
||||||
|
DEVICE_INVALID = 0,
|
||||||
|
DEVICE_AIRSPY_ONE = 1,
|
||||||
|
DEVICE_AIRSPY_HF = 2,
|
||||||
|
DEVICE_RTLSDR = 3,
|
||||||
|
};
|
||||||
|
|
||||||
|
enum CommandType
|
||||||
|
{
|
||||||
|
CMD_HELLO = 0,
|
||||||
|
CMD_GET_SETTING = 1,
|
||||||
|
CMD_SET_SETTING = 2,
|
||||||
|
CMD_PING = 3,
|
||||||
|
};
|
||||||
|
|
||||||
|
enum SettingType
|
||||||
|
{
|
||||||
|
SETTING_STREAMING_MODE = 0,
|
||||||
|
SETTING_STREAMING_ENABLED = 1,
|
||||||
|
SETTING_GAIN = 2,
|
||||||
|
|
||||||
|
SETTING_IQ_FORMAT = 100, // 0x64
|
||||||
|
SETTING_IQ_FREQUENCY = 101, // 0x65
|
||||||
|
SETTING_IQ_DECIMATION = 102, // 0x66
|
||||||
|
SETTING_IQ_DIGITAL_GAIN = 103, // 0x67
|
||||||
|
|
||||||
|
SETTING_FFT_FORMAT = 200, // 0xc8
|
||||||
|
SETTING_FFT_FREQUENCY = 201, // 0xc9
|
||||||
|
SETTING_FFT_DECIMATION = 202, // 0xca
|
||||||
|
SETTING_FFT_DB_OFFSET = 203, // 0xcb
|
||||||
|
SETTING_FFT_DB_RANGE = 204, // 0xcc
|
||||||
|
SETTING_FFT_DISPLAY_PIXELS = 205, // 0xcd
|
||||||
|
};
|
||||||
|
|
||||||
|
enum StreamType
|
||||||
|
{
|
||||||
|
STREAM_TYPE_STATUS = 0,
|
||||||
|
STREAM_TYPE_IQ = 1,
|
||||||
|
STREAM_TYPE_AF = 2,
|
||||||
|
STREAM_TYPE_FFT = 4,
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
enum StreamingMode
|
||||||
|
{
|
||||||
|
STREAM_MODE_IQ_ONLY = STREAM_TYPE_IQ, // 0x01
|
||||||
|
STREAM_MODE_AF_ONLY = STREAM_TYPE_AF, // 0x02
|
||||||
|
STREAM_MODE_FFT_ONLY = STREAM_TYPE_FFT, // 0x04
|
||||||
|
STREAM_MODE_FFT_IQ = STREAM_TYPE_FFT | STREAM_TYPE_IQ, // 0x05
|
||||||
|
STREAM_MODE_FFT_AF = STREAM_TYPE_FFT | STREAM_TYPE_AF, // 0x06
|
||||||
|
};
|
||||||
|
|
||||||
|
enum StreamFormat
|
||||||
|
{
|
||||||
|
STREAM_FORMAT_INVALID = 0,
|
||||||
|
STREAM_FORMAT_UINT8 = 1,
|
||||||
|
STREAM_FORMAT_INT16 = 2,
|
||||||
|
STREAM_FORMAT_INT24 = 3,
|
||||||
|
STREAM_FORMAT_FLOAT = 4,
|
||||||
|
STREAM_FORMAT_DINT4 = 5,
|
||||||
|
};
|
||||||
|
|
||||||
|
enum MessageType
|
||||||
|
{
|
||||||
|
MSG_TYPE_DEVICE_INFO = 0,
|
||||||
|
MSG_TYPE_CLIENT_SYNC = 1,
|
||||||
|
MSG_TYPE_PONG = 2,
|
||||||
|
MSG_TYPE_READ_SETTING = 3,
|
||||||
|
|
||||||
|
MSG_TYPE_UINT8_IQ = 100, // 0x64
|
||||||
|
MSG_TYPE_INT16_IQ = 101, // 0x65
|
||||||
|
MSG_TYPE_INT24_IQ = 102, // 0x66
|
||||||
|
MSG_TYPE_FLOAT_IQ = 103, // 0x67
|
||||||
|
|
||||||
|
MSG_TYPE_UINT8_AF = 200, // 0xc8
|
||||||
|
MSG_TYPE_INT16_AF = 201, // 0xc9
|
||||||
|
MSG_TYPE_INT24_AF = 202, // 0xca
|
||||||
|
MSG_TYPE_FLOAT_AF = 203, // 0xcb
|
||||||
|
|
||||||
|
MSG_TYPE_DINT4_FFT = 300, //0x12C
|
||||||
|
MSG_TYPE_UINT8_FFT = 301, //0x12D
|
||||||
|
};
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#define __attribute__(x)
|
||||||
|
#pragma pack(push, 1)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct ClientHandshake
|
||||||
|
{
|
||||||
|
uint32_t ProtocolVersion;
|
||||||
|
// SDR# doesn't seem to send this
|
||||||
|
//uint32_t ClientNameLength;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct CommandHeader
|
||||||
|
{
|
||||||
|
uint32_t CommandType;
|
||||||
|
uint32_t BodySize;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct SettingTarget
|
||||||
|
{
|
||||||
|
// Again, not used
|
||||||
|
//uint32_t StreamType;
|
||||||
|
uint32_t SettingType;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct MessageHeader
|
||||||
|
{
|
||||||
|
uint32_t ProtocolID;
|
||||||
|
uint32_t MessageType;
|
||||||
|
uint32_t StreamType;
|
||||||
|
uint32_t SequenceNumber;
|
||||||
|
uint32_t BodySize;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct DeviceInfo
|
||||||
|
{
|
||||||
|
uint32_t DeviceType;
|
||||||
|
uint32_t DeviceSerial;
|
||||||
|
uint32_t MaximumSampleRate;
|
||||||
|
uint32_t MaximumBandwidth;
|
||||||
|
uint32_t DecimationStageCount;
|
||||||
|
uint32_t GainStageCount;
|
||||||
|
uint32_t MaximumGainIndex;
|
||||||
|
uint32_t MinimumFrequency;
|
||||||
|
uint32_t MaximumFrequency;
|
||||||
|
uint32_t Resolution;
|
||||||
|
uint32_t MinimumIQDecimation;
|
||||||
|
uint32_t ForcedIQFormat;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct ClientSync
|
||||||
|
{
|
||||||
|
uint32_t CanControl;
|
||||||
|
uint32_t Gain;
|
||||||
|
uint32_t DeviceCenterFrequency;
|
||||||
|
uint32_t IQCenterFrequency;
|
||||||
|
uint32_t FFTCenterFrequency;
|
||||||
|
uint32_t MinimumIQCenterFrequency;
|
||||||
|
uint32_t MaximumIQCenterFrequency;
|
||||||
|
uint32_t MinimumFFTCenterFrequency;
|
||||||
|
uint32_t MaximumFFTCenterFrequency;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct ComplexInt16
|
||||||
|
{
|
||||||
|
int16_t real;
|
||||||
|
int16_t imag;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
struct ComplexUInt8
|
||||||
|
{
|
||||||
|
uint8_t real;
|
||||||
|
uint8_t imag;
|
||||||
|
}__attribute__((packed));
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#pragma pack(pop)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
enum ParserPhase {
|
||||||
|
AcquiringHeader,
|
||||||
|
ReadingData
|
||||||
|
};
|
@ -1,6 +1,6 @@
|
|||||||
#include <core.h>
|
#include <core.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
int main() {
|
int main(int argc, char *argv[]) {
|
||||||
return sdrpp_main();
|
return sdrpp_main(argc, argv);
|
||||||
}
|
}
|