SatDump 2.0.0-alpha-520736c72
Loading...
Searching...
No Matches
block.h
Go to the documentation of this file.
1#pragma once
2
6
7#include "base/dsp_buffer.h"
8#include "core/exception.h"
9#include "dsp/base/stream.h"
10#include "nlohmann/json.hpp"
11#include <mutex>
12#include <thread>
13#include <vector>
14
15namespace satdump
16{
17 namespace ndsp // TODOREWORK back to normal DSP!
18 {
26 {
27 DSP_SAMPLE_TYPE_CF32,
28 DSP_SAMPLE_TYPE_F32,
29 DSP_SAMPLE_TYPE_S16,
30 DSP_SAMPLE_TYPE_S8,
31 DSP_SAMPLE_TYPE_U8,
32 };
33
43 struct BlockIO
44 {
45 std::string name;
46 BlockIOType type;
47 std::shared_ptr<DSPStream> fifo = nullptr;
48 std::shared_ptr<void> blkdata = nullptr;
49
50 // TODOREWORK DOCUMENT
51 uint64_t samplerate = 0;
52 double frequency = 0;
53 };
54
55 // TODOREWORK cleanup!!!!
56 inline void add_param_simple(nlohmann::ordered_json &p, std::string id, std::string type, std::string name = "")
57 {
58 p[id]["type"] = type;
59 if (name != "")
60 p[id]["name"] = name;
61 }
62
63 inline void add_param_range(nlohmann::ordered_json &p, std::string id, std::string type, nlohmann::ordered_json min, nlohmann::ordered_json max, nlohmann::ordered_json step,
64 std::string name = "")
65 {
66 p[id]["type"] = type;
67 if (name != "")
68 p[id]["name"] = name;
69 p[id]["range"] = {min, max, step};
70 }
71
72 inline void add_param_list(nlohmann::ordered_json &p, std::string id, std::string type, nlohmann::json list, std::string name = "")
73 {
74 p[id]["type"] = type;
75 if (name != "")
76 p[id]["name"] = name;
77 p[id]["list"] = list;
78 }
79
100 class Block
101 {
102 public:
103 const std::string d_id;
104
105 protected:
106 std::vector<BlockIO> inputs;
107 std::vector<BlockIO> outputs;
108
109 public:
115 virtual std::vector<BlockIO> get_inputs() { return inputs; }
116
122 virtual std::vector<BlockIO> get_outputs() { return outputs; }
123
131 virtual void set_input(BlockIO f, int i)
132 {
133 if (i >= (int)inputs.size())
134 throw satdump_exception("Input index " + std::to_string(i) + " does not exist for " + d_id + "!");
135 if (inputs[i].type != f.type)
136 throw satdump_exception("Input type " + std::to_string(inputs[i].type) + " not compatible with " + std::to_string(f.type) + " for " + d_id + "!");
137 inputs[i].fifo = f.fifo;
138 }
139
147 virtual BlockIO get_output(int i, int nbuf)
148 {
149 if (i >= (int)outputs.size())
150 throw satdump_exception("Ouput index " + std::to_string(i) + " does not exist for " + d_id + "!");
151 if (nbuf > 0)
152 outputs[i].fifo = std::make_shared<DSPStream>(nbuf);
153 return outputs[i];
154 }
155
169 void link(Block *ptr, int output_index, int input_index, int nbuf) { set_input(ptr->get_output(output_index, nbuf), input_index); }
170
171 private:
172 bool blk_should_run;
173 std::mutex blk_th_mtx;
174 std::thread blk_th;
175 void run()
176 {
177 while (blk_should_run)
178 if (work())
179 break;
180 }
181
182 protected:
188
196 virtual bool work() = 0;
197
198 // TODOREWORK
199 bool is_work_running() { return blk_should_run; }
200
201 public:
208 Block(std::string id, std::vector<BlockIO> in = {}, std::vector<BlockIO> out = {}) : d_id(id), inputs(in), outputs(out)
209 {
210 blk_should_run = false;
211 work_should_exit = false;
212 }
213
214 virtual ~Block()
215 {
216 if (blk_should_run || blk_th.joinable())
217 throw satdump_exception("Block wasn't properly stopped before destructor was called!");
218 }
219
220 public:
230 virtual bool is_async() { return inputs.size() == 0; }
231
232 public:
241 {
242 RES_OK = 0,
243 RES_LISTUPD = 1,
244 RES_IOUPD = 2,
245 RES_ERR = 3,
246 };
247
262 virtual nlohmann::ordered_json get_cfg_list() { return {}; }
263
269 virtual nlohmann::json get_cfg(std::string key) = 0;
270
277 nlohmann::json get_cfg()
278 {
279 nlohmann::json p;
280 auto v = get_cfg_list();
281 for (auto &v2 : v.items())
282 p[v2.key()] = get_cfg(v2.key());
283 return p;
284 }
285
300 virtual cfg_res_t set_cfg(std::string key, nlohmann::json v) = 0;
301
309 cfg_res_t set_cfg(nlohmann::json v)
310 {
311 cfg_res_t r = RES_OK;
312 for (auto &i : v.items())
313 {
314 cfg_res_t r2 = set_cfg(i.key(), i.value());
315 if (r2 > r)
316 r = r2;
317 }
318 return r;
319 }
320
321 protected:
322 template <typename T>
323 void setValFromJSONIfExists(T &v, nlohmann::json p)
324 {
325 if (!p.is_null())
326 v = p.get<T>();
327 }
328
329 protected:
335 virtual void init() {}
336
337 public:
341 virtual void start()
342 {
343 if (blk_should_run || blk_th.joinable())
344 throw satdump_exception("Block wasn't properly stopped before start() was called again!");
345
346 init();
347 work_should_exit = false;
348 blk_should_run = true;
349 blk_th = std::thread(&Block::run, this);
350#ifndef _WIN32
351#ifndef __APPLE__
352 std::string th_id = d_id;
353 th_id.resize(15);
354 pthread_setname_np(blk_th.native_handle(), th_id.c_str());
355#endif
356#endif
357 }
358
372 virtual void stop(bool stop_now = false, bool force = false)
373 { // TODOREWORK allow sending terminator in this function?
374 if (stop_now)
375 work_should_exit = true;
376 if (force)
377 blk_should_run = false;
378
379 blk_th_mtx.lock();
380 if (blk_th.joinable())
381 blk_th.join();
382 blk_th_mtx.unlock();
383 blk_should_run = false;
384 }
385 };
386 } // namespace ndsp
387} // namespace satdump
BlockIOType
Block IO types.
Definition block.h:26
virtual nlohmann::json get_cfg(std::string key)=0
Get parameters of the block as JSON.
cfg_res_t
set_cfg status.
Definition block.h:241
virtual void init()
Applies current parameters to the block. This is called automatically once in start(),...
Definition block.h:335
virtual cfg_res_t set_cfg(std::string key, nlohmann::json v)=0
Set parameters of the block from JSON, including potentially IO configurations for blocks that may ha...
virtual std::vector< BlockIO > get_inputs()
Get the block's input configurations and streams. You should not modify them.
Definition block.h:115
virtual void start()
Starts this block's internal thread and loop.
Definition block.h:341
virtual void set_input(BlockIO f, int i)
Link an input to an output stream of some sort. This also checks the type of the BlockIO to ensure (s...
Definition block.h:131
bool work_should_exit
Used to signal to a block it should exit in order to stop(). Usually only needed in sources.
Definition block.h:187
nlohmann::json get_cfg()
Get parameters of the block as JSON. Unlike get_cfg(key), this returns every single available paramet...
Definition block.h:277
virtual bool work()=0
The actual looping work function meant to handle all the DSP (well, in most blocks)
virtual BlockIO get_output(int i, int nbuf)
Get one of the block's outputs, creating the fifo it if nbuf != 0.
Definition block.h:147
virtual std::vector< BlockIO > get_outputs()
Get the block's output configurations and streams. You should not modify them.
Definition block.h:122
virtual nlohmann::ordered_json get_cfg_list()
Get parameters LIST of the block's parameters. This does not contain actual values,...
Definition block.h:262
Block(std::string id, std::vector< BlockIO > in={}, std::vector< BlockIO > out={})
Generic constructor, to be overloaded.
Definition block.h:208
cfg_res_t set_cfg(nlohmann::json v)
Set parameters of the block from JSON. Essentially the same as set_cfg(key, v), except this will set ...
Definition block.h:309
virtual void stop(bool stop_now=false, bool force=false)
Stops the block, or rather tells the internal loop it should exit & joins the thread to wait....
Definition block.h:372
void link(Block *ptr, int output_index, int input_index, int nbuf)
Link a block's output to another input, more or less just a warper around set_input and set_output.
Definition block.h:169
virtual bool is_async()
Returns true if a block is async. An async block is a block that has outputs without inputs or inputs...
Definition block.h:230
Block IO helper class.
Definition block.h:44