00001 #include "frequencies.h"
00002 #include "frequencytables.h"
00003 #include "channelutil.h"
00004 #include "compat.h"
00005
00006 freq_table_map_t frequencies;
00007
00008 static void init_freq_tables(freq_table_map_t&);
00009
00010 TransportScanItem::TransportScanItem()
00011 : mplexid((uint)-1), FriendlyName(""),
00012 friendlyNum(0), SourceID(0), UseTimer(false),
00013 scanning(false), timeoutTune(1000)
00014 {
00015 bzero(freq_offsets, sizeof(int)*3);
00016
00017 tuning.Clear();
00018 }
00019
00020 TransportScanItem::TransportScanItem(uint sourceid,
00021 const QString &_si_std,
00022 const QString &_name,
00023 uint _mplexid,
00024 uint _timeoutTune)
00025 : mplexid(_mplexid), FriendlyName(_name),
00026 friendlyNum(0), SourceID(sourceid), UseTimer(false),
00027 scanning(false), timeoutTune(_timeoutTune)
00028 {
00029 bzero(freq_offsets, sizeof(int)*3);
00030
00031 tuning.Clear();
00032 tuning.sistandard = _si_std;
00033 }
00034
00035 TransportScanItem::TransportScanItem(uint _sourceid,
00036 const QString &_name,
00037 DTVMultiplex &_tuning,
00038 uint _timeoutTune)
00039 : mplexid(0),
00040 FriendlyName(_name), friendlyNum(0),
00041 SourceID(_sourceid), UseTimer(false),
00042 scanning(false), timeoutTune(_timeoutTune)
00043 {
00044 bzero(freq_offsets, sizeof(int) * 3);
00045 tuning = _tuning;
00046 }
00047
00048 TransportScanItem::TransportScanItem(uint _sourceid,
00049 const QString &_name,
00050 DTVTunerType _tuner_type,
00051 const DTVTransport &_tuning,
00052 uint _timeoutTune)
00053 : mplexid(0),
00054 FriendlyName(_name), friendlyNum(0),
00055 SourceID(_sourceid), UseTimer(false),
00056 scanning(false), timeoutTune(_timeoutTune)
00057 {
00058 bzero(freq_offsets, sizeof(int) * 3);
00059 expectedChannels = _tuning.channels;
00060
00061 tuning.Clear();
00062
00063 tuning.ParseTuningParams(
00064 _tuner_type,
00065 QString::number(_tuning.frequency), _tuning.inversion.toString(),
00066 QString::number(_tuning.symbolrate), _tuning.fec.toString(),
00067 _tuning.polarity.toString(), _tuning.hp_code_rate.toString(),
00068 _tuning.lp_code_rate.toString(), _tuning.modulation.toString(),
00069 _tuning.trans_mode.toString(), _tuning.guard_interval.toString(),
00070 _tuning.hierarchy.toString(), _tuning.modulation.toString(),
00071 _tuning.bandwidth.toString());
00072 }
00073
00074 TransportScanItem::TransportScanItem(uint sourceid,
00075 const QString &std,
00076 const QString &fn,
00077 uint fnum,
00078 uint freq,
00079 const FrequencyTable &ft,
00080 uint tuneTO)
00081 : mplexid(0), FriendlyName(fn),
00082 friendlyNum(fnum), SourceID(sourceid), UseTimer(false),
00083 scanning(false), timeoutTune(tuneTO)
00084 {
00085 bzero(freq_offsets, sizeof(int)*3);
00086
00087 tuning.Clear();
00088
00089
00090 tuning.frequency = freq;
00091 tuning.sistandard = std;
00092 freq_offsets[1] = ft.offset1;
00093 freq_offsets[2] = ft.offset2;
00094
00095 if (std == "dvb")
00096 {
00097 tuning.inversion = ft.inversion;
00098 tuning.bandwidth = ft.bandwidth;
00099 tuning.hp_code_rate = ft.coderate_hp;
00100 tuning.lp_code_rate = ft.coderate_lp;
00101 tuning.modulation = ft.modulation;
00102 tuning.trans_mode = ft.trans_mode;
00103 tuning.guard_interval = ft.guard_interval;
00104 tuning.hierarchy = ft.hierarchy;
00105 }
00106 else
00107 {
00108 tuning.modulation = ft.modulation;
00109 }
00110
00111 mplexid = GetMultiplexIdFromDB();
00112 }
00113
00117 uint TransportScanItem::GetMultiplexIdFromDB(void) const
00118 {
00119 int mplexid = 0;
00120
00121 for (uint i = 0; (i < offset_cnt()) && (mplexid <= 0); i++)
00122 mplexid = ChannelUtil::GetMplexID(SourceID, freq_offset(i));
00123
00124 return mplexid < 0 ? 0 : mplexid;
00125 }
00126
00127 uint64_t TransportScanItem::freq_offset(uint i) const
00128 {
00129 int64_t freq = (int64_t) tuning.frequency;
00130
00131 return (uint64_t) (freq + freq_offsets[i]);
00132 }
00133
00134 QString TransportScanItem::toString() const
00135 {
00136 QString str = QString("Transport Scan Item '%1' #%2\n")
00137 .arg(FriendlyName).arg(friendlyNum);
00138 str += QString("\tmplexid(%1) standard(%2) sourceid(%3)\n")
00139 .arg(mplexid).arg(tuning.sistandard).arg(SourceID);
00140 str += QString("\tUseTimer(%1) scanning(%2)\n")
00141 .arg(UseTimer).arg(scanning);
00142 str += QString("\ttimeoutTune(%3 msec)\n").arg(timeoutTune);
00143 if (tuning.sistandard == "atsc")
00144 {
00145 str += QString("\tfrequency(%1) modulation(%2)\n")
00146 .arg(tuning.frequency)
00147 .arg(tuning.modulation);
00148 }
00149 else
00150 {
00151 str += QString("\tfrequency(%1) constellation(%2)\n")
00152 .arg(tuning.frequency)
00153 .arg(tuning.modulation);
00154 str += QString("\t inv(%1) bandwidth(%2) hp(%3) lp(%4)\n")
00155 .arg(tuning.inversion)
00156 .arg(tuning.bandwidth)
00157 .arg(tuning.hp_code_rate)
00158 .arg(tuning.lp_code_rate);
00159 str += QString("\t trans_mode(%1) guard_int(%2) hierarchy(%3)\n")
00160 .arg(tuning.trans_mode)
00161 .arg(tuning.guard_interval)
00162 .arg(tuning.hierarchy);
00163 }
00164 str += QString("\t offset[0..2]: %1 %2 %3")
00165 .arg(freq_offsets[0]).arg(freq_offsets[1]).arg(freq_offsets[2]);
00166 return str;
00167 }
00168
00169 bool init_freq_tables()
00170 {
00171 static bool statics_initialized = false;
00172 static QMutex statics_lock;
00173 statics_lock.lock();
00174 if (!statics_initialized)
00175 {
00176 init_freq_tables(frequencies);
00177 statics_initialized = true;
00178 }
00179 statics_lock.unlock();
00180
00181 return true;
00182 }
00183 bool just_here_to_force_init = init_freq_tables();
00184
00185 freq_table_list_t get_matching_freq_tables(
00186 QString format, QString modulation, QString country)
00187 {
00188 const freq_table_map_t &fmap = frequencies;
00189
00190 freq_table_list_t list;
00191
00192 QString lookup = QString("%1_%2_%3%4")
00193 .arg(format).arg(modulation).arg(country);
00194
00195 freq_table_map_t::const_iterator it = fmap.begin();
00196 for (uint i = 0; it != fmap.end(); i++)
00197 {
00198 it = fmap.find(lookup.arg(i));
00199 if (it != fmap.end())
00200 list.push_back(*it);
00201 }
00202
00203 return list;
00204 }
00205
00206 long long get_center_frequency(
00207 QString format, QString modulation, QString country, int freqid)
00208 {
00209 freq_table_list_t list =
00210 get_matching_freq_tables(format, modulation, country);
00211
00212 for (uint i = 0; i < list.size(); ++i)
00213 {
00214 int min_freqid = list[i]->name_offset;
00215 int max_freqid = min_freqid +
00216 ((list[i]->frequencyEnd - list[i]->frequencyStart) /
00217 list[i]->frequencyStep);
00218
00219 if ((min_freqid <= freqid) && (freqid <= max_freqid))
00220 return list[i]->frequencyStart +
00221 list[i]->frequencyStep * (freqid - min_freqid);
00222 }
00223 return -1;
00224 }
00225
00226 int get_closest_freqid(
00227 QString format, QString modulation, QString country, long long centerfreq)
00228 {
00229 modulation = (modulation == "8vsb") ? "vsb8" : modulation;
00230
00231 freq_table_list_t list =
00232 get_matching_freq_tables(format, modulation, country);
00233
00234 for (uint i = 0; i < list.size(); ++i)
00235 {
00236 int min_freqid = list[i]->name_offset;
00237 int max_freqid = min_freqid +
00238 ((list[i]->frequencyEnd - list[i]->frequencyStart) /
00239 list[i]->frequencyStep);
00240 int freqid =
00241 ((centerfreq - list[i]->frequencyStart) /
00242 list[i]->frequencyStep) + min_freqid;
00243
00244 if ((min_freqid <= freqid) && (freqid <= max_freqid))
00245 return freqid;
00246 }
00247
00248
00249
00250 return -1;
00251 }
00252
00253
00254 static void init_freq_tables(freq_table_map_t &fmap)
00255 {
00256
00257 fmap["dvbt_ofdm_uk0"] = new FrequencyTable(
00258 474000000, 850000000, 8000000, "" , 0, DTVInversion::kInversionOff,
00259 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFECAuto,
00260 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAMAuto,
00261 DTVTransmitMode::kTransmissionMode2K,
00262 DTVGuardInterval::kGuardInterval_1_32, DTVHierarchy::kHierarchyNone,
00263 DTVModulation::kModulationQAMAuto, 166670, -166670);
00264
00265
00266 fmap["dvbt_ofdm_fi0"] = new FrequencyTable(
00267 474000000, 850000000, 8000000, "", 0, DTVInversion::kInversionOff,
00268 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFECAuto,
00269 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAM64,
00270 DTVTransmitMode::kTransmissionModeAuto,
00271 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00272 DTVModulation::kModulationQAMAuto, 0, 0);
00273
00274
00275 fmap["dvbt_ofdm_se0"] = new FrequencyTable(
00276 474000000, 850000000, 8000000, "", 0, DTVInversion::kInversionOff,
00277 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFECAuto,
00278 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAM64,
00279 DTVTransmitMode::kTransmissionModeAuto,
00280 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00281 DTVModulation::kModulationQAMAuto, 0, 0);
00282
00283
00284 fmap["dvbt_ofdm_au0"] = new FrequencyTable(
00285 177500000, 226500000, 7000000, "", 0, DTVInversion::kInversionOff,
00286 DTVBandwidth::kBandwidth7MHz, DTVCodeRate::kFECAuto,
00287 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAM64,
00288 DTVTransmitMode::kTransmissionMode8K, DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00289 DTVModulation::kModulationQAMAuto, 125000, 0);
00290 fmap["dvbt_ofdm_au1"] = new FrequencyTable(
00291 529500000, 816500000, 7000000, "", 0, DTVInversion::kInversionOff,
00292 DTVBandwidth::kBandwidth7MHz, DTVCodeRate::kFECAuto,
00293 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAM64,
00294 DTVTransmitMode::kTransmissionMode8K,
00295 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00296 DTVModulation::kModulationQAMAuto, 125000, 0);
00297
00298
00299 fmap["dvbt_ofdm_de0"] = new FrequencyTable(
00300 177500000, 226500000, 7000000, "", 0, DTVInversion::kInversionOff,
00301 DTVBandwidth::kBandwidth7MHz, DTVCodeRate::kFECAuto,
00302 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAMAuto,
00303 DTVTransmitMode::kTransmissionMode8K,
00304 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00305 DTVModulation::kModulationQAMAuto, 125000, 0);
00306 fmap["dvbt_ofdm_de1"] = new FrequencyTable(
00307 474000000, 826000000, 8000000, "", 0, DTVInversion::kInversionOff,
00308 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFECAuto,
00309 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAMAuto,
00310 DTVTransmitMode::kTransmissionModeAuto,
00311 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00312 DTVModulation::kModulationQAMAuto, 125000, 0);
00313
00314
00315 fmap["dvbt_ofdm_es0"] = new FrequencyTable(
00316 474000000, 858000000, 8000000, "", 0, DTVInversion::kInversionOff,
00317 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFECAuto,
00318 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAMAuto,
00319 DTVTransmitMode::kTransmissionModeAuto,
00320 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00321 DTVModulation::kModulationQAMAuto, 125000, 0);
00322
00323
00324 fmap["dvbt_ofdm_nz0"] = new FrequencyTable(
00325 474000000, 858000000, 8000000, "", 0, DTVInversion::kInversionOff,
00326 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFEC_3_4,
00327 DTVCodeRate::kFEC_3_4, DTVModulation::kModulationQAM64,
00328 DTVTransmitMode::kTransmissionMode8K,
00329 DTVGuardInterval::kGuardInterval_1_16, DTVHierarchy::kHierarchyNone,
00330 DTVModulation::kModulationQAM64, 0 , 0);
00331
00332
00333 fmap["dvbt_ofdm_fr0"] = new FrequencyTable(
00334 474000000, 850000000, 8000000, "" , 0, DTVInversion::kInversionOff,
00335 DTVBandwidth::kBandwidth8MHz, DTVCodeRate::kFECAuto,
00336 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAMAuto,
00337 DTVTransmitMode::kTransmissionMode8K,
00338 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00339 DTVModulation::kModulationQAMAuto, 167000, -166000);
00340
00341
00342 #ifdef DEBUG_DVB_OFFSETS
00343
00344 fmap["atsc_vsb8_us0"] = new FrequencyTable(
00345 533000000, 803000000, 6000000, "xATSC Channel %1", 24,
00346 DTVInversion::kInversionOff,
00347 DTVBandwidth::kBandwidth7MHz, DTVCodeRate::kFECAuto,
00348 DTVCodeRate::kFECAuto, DTVModulation::kModulationQAMAuto,
00349 DTVTransmitMode::kTransmissionMode8K,
00350 DTVGuardInterval::kGuardIntervalAuto, DTVHierarchy::kHierarchyNone,
00351 DTVModulation::kModulation8VSB, -100000, 100000);
00352 #else // if !DEBUG_DVB_OFFSETS
00353
00354
00355 fmap["atsc_vsb8_us0"] = new FrequencyTable(
00356 "ATSC Channel %1", 2, 57000000, 69000000, 6000000,
00357 DTVModulation::kModulation8VSB);
00358
00359 fmap["atsc_vsb8_us1"] = new FrequencyTable(
00360 "ATSC Channel %1", 5, 79000000, 85000000, 6000000,
00361 DTVModulation::kModulation8VSB);
00362
00363 fmap["atsc_vsb8_us2"] = new FrequencyTable(
00364 "ATSC Channel %1", 7, 177000000, 213000000, 6000000,
00365 DTVModulation::kModulation8VSB);
00366
00367 fmap["atsc_vsb8_us3"] = new FrequencyTable(
00368 "ATSC Channel %1", 14, 473000000, 803000000, 6000000,
00369 DTVModulation::kModulation8VSB);
00370
00371 fmap["atsc_vsb8_us4"] = new FrequencyTable(
00372 "ATSC Channel %1", 70, 809000000, 887000000, 6000000,
00373 DTVModulation::kModulation8VSB);
00374 #endif // !DEBUG_DVB_OFFSETS
00375
00376 QString modStr[] = { "vsb8", "qam256", "qam128", "qam64", };
00377 uint mod[] = { DTVModulation::kModulation8VSB,
00378 DTVModulation::kModulationQAM256,
00379 DTVModulation::kModulationQAM128,
00380 DTVModulation::kModulationQAM64, };
00381 QString desc[] = { "ATSC ", "QAM-256 ", "QAM-128 ", "QAM-64 ", };
00382
00383 #define FREQ(A,B, C,D, E,F,G, H, I) \
00384 fmap[QString("atsc_%1_us%2").arg(A).arg(B)] = \
00385 new FrequencyTable(C+D, E, F, G, H, I);
00386
00387
00388 #define US_MAX_CHAN 159
00389
00390
00391 #define EIA_542_FREQUENCY(A,B,C) ( ( A * ( 8 + C ) ) + B )
00392
00393 for (uint i = 0; i < 4; i++)
00394 {
00395
00396 FREQ(modStr[i], "cable0", desc[i], "Channel %1",
00397 2, 57000000, 69000000, 6000000, mod[i]);
00398 FREQ(modStr[i], "cable1", desc[i], "Channel %1",
00399 5, 79000000, 85000000, 6000000, mod[i]);
00400 FREQ(modStr[i], "cable2", desc[i], "Channel %1",
00401 7, 177000000, 213000000, 6000000, mod[i]);
00402 FREQ(modStr[i], "cable3", desc[i], "Channel %1",
00403 14, 123000000, 171000000, 6000000, mod[i]);
00404 FREQ(modStr[i], "cable4", desc[i], "Channel %1",
00405 23, 219000000, 645000000, 6000000, mod[i]);
00406 FREQ(modStr[i], "cable5", desc[i], "Channel %1",
00407 95, 93000000, 117000000, 6000000, mod[i]);
00408
00409
00410 FREQ(modStr[i], "cable6", desc[i], "Channel %1",
00411 100, 651000000,
00412 EIA_542_FREQUENCY(6000000, 3000000, US_MAX_CHAN),
00413 6000000, mod[i]);
00414 FREQ(modStr[i], "cable7", desc[i], "Channel T-%1",
00415 7, 8750000, 50750000, 6000000, mod[i]);
00416
00417
00418 FREQ(modStr[i], "cablehigh0", desc[i], "Channel %1",
00419 78, 549000000, 645000000, 6000000, mod[i]);
00420 FREQ(modStr[i], "cablehigh1", desc[i], "Channel %1",
00421 100, 651000000,
00422 EIA_542_FREQUENCY(6000000, 3000000, US_MAX_CHAN),
00423 6000000, mod[i]);
00424
00425
00426 FREQ(modStr[i], "hrc0", desc[i], "HRC %1",
00427 1, 73753600, 73753601, 6000300, mod[i]);
00428 FREQ(modStr[i], "hrc1", desc[i], "HRC %1",
00429 2, 55752700, 67753300, 6000300, mod[i]);
00430 FREQ(modStr[i], "hrc2", desc[i], "HRC %1",
00431 5, 79753900, 85754200, 6000300, mod[i]);
00432 FREQ(modStr[i], "hrc3", desc[i], "HRC %1",
00433 7, 175758700, 211760500, 6000300, mod[i]);
00434 FREQ(modStr[i], "hrc4", desc[i], "HRC %1",
00435 14, 121756000, 169758400, 6000300, mod[i]);
00436 FREQ(modStr[i], "hrc5", desc[i], "HRC %1",
00437 23, 217760800, 643782100, 6000300, mod[i]);
00438 FREQ(modStr[i], "hrc6", desc[i], "HRC %1",
00439 95, 91754500, 115755700, 6000300, mod[i]);
00440
00441
00442 FREQ(modStr[i], "hrc7", desc[i], "HRC %1",
00443 100, 649782400,
00444 EIA_542_FREQUENCY(6000300, 1750000, US_MAX_CHAN),
00445 6000300, mod[i]);
00446
00447
00448
00449 FREQ(modStr[i], "hrchigh0", desc[i], "HRC %1",
00450 76, 535776700, 643782100, 6000300, mod[i]);
00451 FREQ(modStr[i], "hrchigh1", desc[i], "HRC %1",
00452 100, 649782400,
00453 EIA_542_FREQUENCY(6000300, 1750000, US_MAX_CHAN),
00454 6000300, mod[i]);
00455
00456
00457 FREQ(modStr[i], "irc0", desc[i], "IRC %1",
00458 1, 75012500, 75012501, 6000000, mod[i]);
00459 FREQ(modStr[i], "irc1", desc[i], "IRC %1",
00460 2, 57012500, 69012500, 6000000, mod[i]);
00461 FREQ(modStr[i], "irc2", desc[i], "IRC %1",
00462 5, 81012500, 87012500, 6000000, mod[i]);
00463 FREQ(modStr[i], "irc3", desc[i], "IRC %1",
00464 7, 177012500, 213012500, 6000000, mod[i]);
00465 FREQ(modStr[i], "irc4", desc[i], "IRC %1",
00466 14, 123012500, 171012500, 6000000, mod[i]);
00467 FREQ(modStr[i], "irc5", desc[i], "IRC %1",
00468 23, 219012500, 327012500, 6000000, mod[i]);
00469 FREQ(modStr[i], "irc6", desc[i], "IRC %1",
00470 42, 333025000, 333025001, 6000000, mod[i]);
00471 FREQ(modStr[i], "irc7", desc[i], "IRC %1",
00472 43, 339012500, 645012500, 6000000, mod[i]);
00473 FREQ(modStr[i], "irc8", desc[i], "IRC %1",
00474 95, 93012500, 105012500, 6000000, mod[i]);
00475 FREQ(modStr[i], "irc9", desc[i], "IRC %1",
00476 98, 111025000, 117025000, 6000000, mod[i]);
00477
00478
00479 FREQ(modStr[i], "irc10", desc[i], "IRC %1",
00480 100, 651012500,
00481 EIA_542_FREQUENCY(6000000, 3012500, US_MAX_CHAN),
00482 6000000, mod[i]);
00483
00484
00485
00486 FREQ(modStr[i], "irchigh0", desc[i], "IRC %1",
00487 76, 537012500, 645012500, 6000000, mod[i]);
00488 FREQ(modStr[i], "irchigh1", desc[i], "IRC %1",
00489 100, 651012500,
00490 EIA_542_FREQUENCY(6000000, 3012500, US_MAX_CHAN),
00491 6000000, mod[i]);
00492 }
00493
00494
00495 for (struct CHANLISTS *ptr = chanlists; ptr->name ; ptr++)
00496 {
00497 QString tbl_name = ptr->name;
00498 for (uint i = 0; i < (uint)ptr->count; i++)
00499 {
00500 uint64_t freq = (ptr->list[i].freq * 1000LL) + 1750000;
00501 fmap[QString("analog_analog_%1%2").arg(tbl_name).arg(i)] =
00502 new FrequencyTable(
00503 QString("%1 %2").arg(tbl_name).arg(ptr->list[i].name), i+2,
00504 freq, freq + 3000000,
00505 6000000, DTVModulation::kModulationAnalog);
00506 }
00507 }
00508
00509 }