1 /* 2 * Copyright (C) 2018 3 * Matthias P. Braendli (matthias.braendli@mpb.li) 4 * 5 * Copyright (C) 2017 6 * Albrecht Lohofener (albrechtloh@gmx.de) 7 * 8 * This file is based on SDR-J 9 * Copyright (C) 2010, 2011, 2012 10 * Jan van Katwijk (J.vanKatwijk@gmail.com) 11 * 12 * This file is part of the welle.io. 13 * Many of the ideas as implemented in welle.io are derived from 14 * other work, made available through the GNU general Public License. 15 * All copyrights of the original authors are recognized. 16 * 17 * welle.io is free software; you can redistribute it and/or modify 18 * it under the terms of the GNU General Public License as published by 19 * the Free Software Foundation; either version 2 of the License, or 20 * (at your option) any later version. 21 * 22 * welle.io is distributed in the hope that it will be useful, 23 * but WITHOUT ANY WARRANTY; without even the implied warranty of 24 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 25 * GNU General Public License for more details. 26 * 27 * You should have received a copy of the GNU General Public License 28 * along with welle.io; if not, write to the Free Software 29 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 30 * 31 */ 32 33 #ifndef RADIOCONTROLLER_H 34 #define RADIOCONTROLLER_H 35 36 #include <cstddef> 37 #include <vector> 38 #include <string> 39 #include <complex> 40 #include "dab-constants.h" 41 42 struct dab_date_time_t { 43 int year = 0; 44 int month = 0; 45 int day = 0; 46 int hour = 0; 47 int minutes = 0; 48 int seconds = 0; 49 50 // Information decoded from local time offset in FIG 0/9 51 int hourOffset = 0; 52 int minuteOffset = 0; 53 }; 54 55 56 struct tii_measurement_t { 57 int comb = 0; 58 int pattern = 0; 59 float error = 0; 60 int delay_samples = 0; 61 62 float getDelayKm(void) const; 63 }; 64 65 struct mot_file_t { 66 std::vector<uint8_t> data; 67 int content_sub_type; 68 69 std::string content_name; 70 std::string click_through_url; 71 uint8_t category; 72 uint8_t slide_id; 73 std::string category_title; 74 }; 75 76 enum class message_level_t { Information, Error }; 77 78 /* Definition of the interface all radio controllers must implement. 79 * The RadioController handles events that are common to all programmes 80 * being listened to. 81 * All functions starting with "on" are callbacks for the backend. 82 */ 83 class RadioControllerInterface { 84 public: 85 /* Signal-to-Noise Ratio was calculated. snr is a value in dB. */ 86 virtual void onSNR(float snr) = 0; 87 88 /* The frequency corrector estimated a new correction. The frequency 89 * correction consists of a coarse and a fine value, both having the 90 * same units, measured in number of samples. */ 91 virtual void onFrequencyCorrectorChange(int fine, int coarse) = 0; 92 93 /* Indicate if receive signal synchronisation was acquired or lost. */ 94 virtual void onSyncChange(char isSync) = 0; 95 96 /* Indicate if a signal is suspected on the currently tuned frequency. 97 * This is useful to accelerate the scan. */ 98 virtual void onSignalPresence(bool isSignal) = 0; 99 100 /* A new service with service ID sId was detected. */ 101 virtual void onServiceDetected(uint32_t sId) = 0; 102 103 /* When the ensemble changes */ 104 virtual void onNewEnsemble(uint16_t eId) = 0; 105 106 /* When the ensemble label changes */ 107 virtual void onSetEnsembleLabel(DabLabel& label) = 0; 108 109 virtual void onDateTimeUpdate(const dab_date_time_t& dateTime) = 0; 110 111 /* For every FIB, tell if the CRC check passed. fib points to a bit-vector with 256 bits of FIB data */ 112 virtual void onFIBDecodeSuccess(bool crcCheckOk, const uint8_t* fib) = 0; 113 114 /* When a new channel impulse response vector was calculated */ 115 virtual void onNewImpulseResponse(std::vector<float>&& data) = 0; 116 117 /* When new constellation points are available. data contains 118 * (L-1) * K / OfdmDecoder::constellationDecimation points. */ 119 virtual void onConstellationPoints(std::vector<DSPCOMPLEX>&& data) = 0; 120 121 /* When a new null symbol vector was received. 122 * Data contains the samples of the complete NULL symbol. */ 123 virtual void onNewNullSymbol(std::vector<DSPCOMPLEX>&& data) = 0; 124 125 /* When TII information for a comb/pattern pair is available */ 126 virtual void onTIIMeasurement(tii_measurement_t&& m) = 0; 127 128 /* When a information or warning message should be printed */ 129 virtual void onMessage(message_level_t level, const std::string& text, const std::string& text2 = std::string()) = 0; 130 131 /* The receiver has shutdown due to a failure in the input device */ onInputFailure(void)132 virtual void onInputFailure(void) { }; 133 }; 134 135 /* A Programme Hander is associated to each tuned programme in the ensemble. 136 */ 137 class ProgrammeHandlerInterface { 138 public: 139 /* Count the number of frame errors from the MP2, AAC or data 140 * decoder. */ 141 virtual void onFrameErrors(int frameErrors) = 0; 142 143 /* New audio data is available. The sampleRate and the 144 * stereo indicator may change at any time. 145 * mode is an information related to the audio encoding 146 * used. */ 147 virtual void onNewAudio(std::vector<int16_t>&& audioData, int sampleRate, const std::string& mode) = 0; 148 149 /* (DAB+ only) Reed-Solomon decoding error indicator, and 150 * number of corrected errors. 151 * The function will also be called in the absence of errors, 152 * with an count of 0. */ 153 virtual void onRsErrors(bool uncorrectedErrors, int numCorrectedErrors) = 0; 154 155 /* (DAB+ only) Audio Decoder error */ 156 virtual void onAacErrors(int aacErrors) = 0; 157 158 /* A new Dynamic Label was decoded. 159 * label is utf-8 encoded. */ 160 virtual void onNewDynamicLabel(const std::string& label) = 0; 161 162 /* A slide was decoded. data contains the raw bytes, and subtype 163 * defines the data format: 164 * 0x01 for JPEG, 0x03 for PNG */ 165 virtual void onMOT(const mot_file_t& mot_file) = 0; 166 167 /* Called when the PAD decoder notices a mismatch between announced 168 * and effective X-PAD length. 169 */ 170 virtual void onPADLengthError(size_t announced_xpad_len, size_t xpad_len) = 0; 171 }; 172 173 enum class DeviceParam { 174 BiasTee, 175 SoapySDRAntenna, 176 SoapySDRDriverArgs, 177 SoapySDRClockSource, 178 }; 179 180 /* Definition of the interface all input devices must implement */ 181 class InputInterface { 182 public: ~InputInterface()183 virtual ~InputInterface() {} 184 virtual void setFrequency(int frequency) = 0; 185 virtual int getFrequency(void) const = 0; 186 virtual bool is_ok(void) = 0; 187 virtual bool restart(void) = 0; 188 virtual void stop(void) = 0; 189 virtual void reset(void) = 0; 190 virtual int32_t getSamples(DSPCOMPLEX* buffer, int32_t size) = 0; 191 virtual std::vector<DSPCOMPLEX> getSpectrumSamples(int size) = 0; 192 virtual int32_t getSamplesToRead(void) = 0; 193 virtual float setGain(int gain) = 0; 194 virtual float getGain(void) const = 0; 195 virtual int getGainCount(void) = 0; 196 virtual void setAgc(bool agc) = 0; 197 virtual std::string getDescription(void) = 0; 198 setDeviceParam(DeviceParam param,int value)199 virtual bool setDeviceParam(DeviceParam param, int value) { 200 (void)param; (void)value; 201 return false; 202 } 203 setDeviceParam(DeviceParam param,const std::string & value)204 virtual bool setDeviceParam(DeviceParam param, const std::string& value) { 205 (void)param; (void)value; 206 return false; 207 } 208 }; 209 210 #endif 211