1 /*
2
3 dvbstream
4 (C) Dave Chapman <dave@dchapman.com> 2001, 2002.
5 (C) Rozhuk Ivan <rozhuk.im@gmail.com> 2016 - 2017
6
7 Original authors: Nico, probably Arpi
8
9 Some code based on dvbstream, 0.4.3-pre3 (CVS checkout),
10 http://sourceforge.net/projects/dvbtools/
11
12 Modified for use with MPlayer, for details see the changelog at
13 http://svn.mplayerhq.hu/mplayer/trunk/
14 $Id$
15
16 Copyright notice:
17
18 This program is free software; you can redistribute it and/or modify
19 it under the terms of the GNU General Public License as published by
20 the Free Software Foundation; either version 2 of the License, or
21 (at your option) any later version.
22
23 This program is distributed in the hope that it will be useful,
24 but WITHOUT ANY WARRANTY; without even the implied warranty of
25 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26 GNU General Public License for more details.
27
28 You should have received a copy of the GNU General Public License
29 along with this program; if not, write to the Free Software
30 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
31
32 */
33
34 #include "config.h"
35 #include <stdio.h>
36 #include <stdlib.h>
37 #include <string.h>
38 #include <sys/ioctl.h>
39 #include <sys/time.h>
40 #include <poll.h>
41 #include <unistd.h>
42 #include <fcntl.h>
43 #include <errno.h>
44 #include <pthread.h>
45
46 #include <libavutil/avstring.h>
47
48 #include "osdep/io.h"
49 #include "misc/ctype.h"
50 #include "osdep/timer.h"
51
52 #include "stream.h"
53 #include "common/tags.h"
54 #include "options/m_config.h"
55 #include "options/m_option.h"
56 #include "options/options.h"
57 #include "options/path.h"
58
59 #include "dvbin.h"
60 #include "dvb_tune.h"
61
62 #if !HAVE_GPL
63 #error GPL only
64 #endif
65
66 #define CHANNEL_LINE_LEN 256
67 #define min(a, b) ((a) <= (b) ? (a) : (b))
68
69 #define OPT_BASE_STRUCT dvb_opts_t
70
71 static dvb_state_t *global_dvb_state = NULL;
72 static pthread_mutex_t global_dvb_state_lock = PTHREAD_MUTEX_INITIALIZER;
73
74 const struct m_sub_options stream_dvb_conf = {
75 .opts = (const m_option_t[]) {
76 {"prog", OPT_STRING(cfg_prog), .flags = UPDATE_DVB_PROG},
77 {"card", OPT_INT(cfg_devno), M_RANGE(0, MAX_ADAPTERS-1)},
78 {"timeout", OPT_INT(cfg_timeout), M_RANGE(1, 30)},
79 {"file", OPT_STRING(cfg_file), .flags = M_OPT_FILE},
80 {"full-transponder", OPT_FLAG(cfg_full_transponder)},
81 {"channel-switch-offset", OPT_INT(cfg_channel_switch_offset),
82 .flags = UPDATE_DVB_PROG},
83 {0}
84 },
85 .size = sizeof(dvb_opts_t),
86 .defaults = &(const dvb_opts_t){
87 .cfg_prog = NULL,
88 .cfg_devno = 0,
89 .cfg_timeout = 30,
90 },
91 };
92
93 void dvbin_close(stream_t *stream);
94
parse_vdr_modulation(const char ** modstring)95 static fe_modulation_t parse_vdr_modulation(const char** modstring) {
96 if (!strncmp(*modstring, "16", 2)) {
97 (*modstring)+=2;
98 return QAM_16;
99 } else if (!strncmp(*modstring, "32", 2)) {
100 (*modstring)+=2;
101 return QAM_32;
102 } else if (!strncmp(*modstring, "64", 2)) {
103 (*modstring)+=2;
104 return QAM_64;
105 } else if (!strncmp(*modstring, "128", 3)) {
106 (*modstring)+=3;
107 return QAM_128;
108 } else if (!strncmp(*modstring, "256", 3)) {
109 (*modstring)+=3;
110 return QAM_256;
111 } else if (!strncmp(*modstring, "998", 3)) {
112 (*modstring)+=3;
113 return QAM_AUTO;
114 } else if (!strncmp(*modstring, "2", 1)) {
115 (*modstring)++;
116 return QPSK;
117 } else if (!strncmp(*modstring, "5", 1)) {
118 (*modstring)++;
119 return PSK_8;
120 } else if (!strncmp(*modstring, "6", 1)) {
121 (*modstring)++;
122 return APSK_16;
123 } else if (!strncmp(*modstring, "7", 1)) {
124 (*modstring)++;
125 return APSK_32;
126 } else if (!strncmp(*modstring, "10", 2)) {
127 (*modstring)+=2;
128 return VSB_8;
129 } else if (!strncmp(*modstring, "11", 2)) {
130 (*modstring)+=2;
131 return VSB_16;
132 } else if (!strncmp(*modstring, "12", 2)) {
133 (*modstring)+=2;
134 return DQPSK;
135 } else {
136 return QAM_AUTO;
137 }
138 }
139
parse_vdr_par_string(const char * vdr_par_str,dvb_channel_t * ptr)140 static void parse_vdr_par_string(const char *vdr_par_str, dvb_channel_t *ptr)
141 {
142 //FIXME: There is more information in this parameter string, especially related
143 // to non-DVB-S reception.
144 if (vdr_par_str[0]) {
145 const char *vdr_par = &vdr_par_str[0];
146 while (vdr_par && *vdr_par) {
147 switch (mp_toupper(*vdr_par)) {
148 case 'H':
149 ptr->pol = 'H';
150 vdr_par++;
151 break;
152 case 'V':
153 ptr->pol = 'V';
154 vdr_par++;
155 break;
156 case 'S':
157 vdr_par++;
158 if (*vdr_par == '1') {
159 ptr->is_dvb_x2 = true;
160 } else {
161 ptr->is_dvb_x2 = false;
162 }
163 vdr_par++;
164 break;
165 case 'P':
166 vdr_par++;
167 char *endptr = NULL;
168 errno = 0;
169 int n = strtol(vdr_par, &endptr, 10);
170 if (!errno && endptr != vdr_par) {
171 ptr->stream_id = n;
172 vdr_par = endptr;
173 }
174 break;
175 case 'I':
176 vdr_par++;
177 if (*vdr_par == '1') {
178 ptr->inv = INVERSION_ON;
179 } else {
180 ptr->inv = INVERSION_OFF;
181 }
182 vdr_par++;
183 break;
184 case 'M':
185 vdr_par++;
186 ptr->mod = parse_vdr_modulation(&vdr_par);
187 break;
188 default:
189 vdr_par++;
190 }
191 }
192 }
193 }
194
dvb_strtok_r(char * s,const char * sep,char ** p)195 static char *dvb_strtok_r(char *s, const char *sep, char **p)
196 {
197 if (!s && !(s = *p))
198 return NULL;
199
200 /* Skip leading separators. */
201 s += strspn(s, sep);
202
203 /* s points at first non-separator, or end of string. */
204 if (!*s)
205 return *p = 0;
206
207 /* Move *p to next separator. */
208 *p = s + strcspn(s, sep);
209 if (**p) {
210 *(*p)++ = 0;
211 } else {
212 *p = 0;
213 }
214 return s;
215 }
216
parse_pid_string(struct mp_log * log,char * pid_string,dvb_channel_t * ptr)217 static bool parse_pid_string(struct mp_log *log, char *pid_string,
218 dvb_channel_t *ptr)
219 {
220 if (pid_string[0]) {
221 int pcnt = 0;
222 /* These tokens also catch vdr-style PID lists.
223 * They can contain 123=deu@3,124=eng+jap@4;125
224 * 3 and 4 are codes for codec type, =langLeft+langRight is allowed,
225 * and ; may separate a dolby channel.
226 * With the numChars-test and the full token-list, all is handled
227 * gracefully.
228 */
229 const char *tokens = "+,;";
230 char *pidPart;
231 char *savePtr = NULL;
232 pidPart = dvb_strtok_r(pid_string, tokens, &savePtr);
233 while (pidPart != NULL) {
234 if (ptr->pids_cnt >= DMX_FILTER_SIZE - 1) {
235 mp_verbose(log, "Maximum number of PIDs for one channel "
236 "reached, ignoring further ones!\n");
237 return pcnt > 0;
238 }
239 int numChars = 0;
240 int pid = 0;
241 pcnt += sscanf(pidPart, "%d%n", &pid, &numChars);
242 if (numChars > 0) {
243 ptr->pids[ptr->pids_cnt] = pid;
244 ptr->pids_cnt++;
245 }
246 pidPart = dvb_strtok_r(NULL, tokens, &savePtr);
247 }
248 if (pcnt > 0)
249 return true;
250 }
251 return false;
252 }
253
dvb_get_channels(struct mp_log * log,dvb_channels_list_t * list_add,int cfg_full_transponder,char * filename,unsigned int frontend,int delsys,unsigned int delsys_mask)254 static dvb_channels_list_t *dvb_get_channels(struct mp_log *log,
255 dvb_channels_list_t *list_add,
256 int cfg_full_transponder,
257 char *filename,
258 unsigned int frontend,
259 int delsys, unsigned int delsys_mask)
260 {
261 dvb_channels_list_t *list = list_add;
262 FILE *f;
263 char line[CHANNEL_LINE_LEN], *colon;
264
265 if (!filename)
266 return NULL;
267
268 int fields, cnt, k;
269 int has8192, has0;
270 dvb_channel_t *ptr, *tmp, chn;
271 char tmp_lcr[256], tmp_hier[256], inv[256], bw[256], cr[256], mod[256],
272 transm[256], gi[256], vpid_str[256], apid_str[256], tpid_str[256],
273 vdr_par_str[256], vdr_loc_str[256];
274 const char *cbl_conf =
275 "%d:%255[^:]:%d:%255[^:]:%255[^:]:%255[^:]:%255[^:]\n";
276 const char *sat_conf = "%d:%c:%d:%d:%255[^:]:%255[^:]\n";
277 const char *ter_conf =
278 "%d:%255[^:]:%255[^:]:%255[^:]:%255[^:]:%255[^:]:%255[^:]:%255[^:]:%255[^:]:%255[^:]:%255[^:]\n";
279 #ifdef DVB_ATSC
280 const char *atsc_conf = "%d:%255[^:]:%255[^:]:%255[^:]\n";
281 #endif
282 const char *vdr_conf =
283 "%d:%255[^:]:%255[^:]:%d:%255[^:]:%255[^:]:%255[^:]:%*255[^:]:%d:%*d:%*d:%*d\n%n";
284
285 mp_verbose(log, "CONFIG_READ FILE: %s, type: %s\n",
286 filename, get_dvb_delsys(delsys));
287 if ((f = fopen(filename, "r")) == NULL) {
288 mp_fatal(log, "CAN'T READ CONFIG FILE %s\n", filename);
289 return NULL;
290 }
291
292 if (list == NULL) {
293 list = malloc(sizeof(dvb_channels_list_t));
294 if (list == NULL) {
295 fclose(f);
296 mp_verbose(log, "DVB_GET_CHANNELS: couldn't malloc enough memory\n");
297 return NULL;
298 }
299 memset(list, 0x00, sizeof(dvb_channels_list_t));
300 }
301
302 ptr = &chn;
303 while (!feof(f)) {
304 if (fgets(line, CHANNEL_LINE_LEN, f) == NULL)
305 continue;
306
307 if ((line[0] == '#') || (strlen(line) == 0))
308 continue;
309
310 memset(ptr, 0x00, sizeof(dvb_channel_t));
311 vpid_str[0] = apid_str[0] = tpid_str[0] = 0;
312 vdr_loc_str[0] = vdr_par_str[0] = 0;
313
314 colon = strchr(line, ':');
315 if (colon) {
316 k = colon - line;
317 if (!k)
318 continue;
319 // In some modern VDR-style configs, channel name also has bouquet after ;.
320 // Parse that off, we ignore it.
321 char *bouquet_sep = strchr(line, ';');
322 int channel_name_length = k;
323 if (bouquet_sep && bouquet_sep < colon)
324 channel_name_length = (bouquet_sep - line);
325 ptr->name = malloc((channel_name_length + 1));
326 if (!ptr->name)
327 continue;
328 av_strlcpy(ptr->name, line, (channel_name_length + 1));
329 } else {
330 continue;
331 }
332 k++;
333 ptr->pids_cnt = 0;
334 ptr->freq = 0;
335 ptr->service_id = -1;
336 ptr->is_dvb_x2 = false;
337 ptr->frontend = frontend;
338 ptr->delsys = delsys;
339 ptr->diseqc = 0;
340 ptr->stream_id = NO_STREAM_ID_FILTER;
341 ptr->inv = INVERSION_AUTO;
342 ptr->bw = BANDWIDTH_AUTO;
343 ptr->cr = FEC_AUTO;
344 ptr->cr_lp = FEC_AUTO;
345 ptr->mod = QAM_AUTO;
346 ptr->hier = HIERARCHY_AUTO;
347 ptr->gi = GUARD_INTERVAL_AUTO;
348 ptr->trans = TRANSMISSION_MODE_AUTO;
349
350 // Check if VDR-type channels.conf-line - then full line is consumed by the scan.
351 int num_chars = 0;
352 fields = sscanf(&line[k], vdr_conf,
353 &ptr->freq, vdr_par_str, vdr_loc_str, &ptr->srate,
354 vpid_str, apid_str, tpid_str, &ptr->service_id,
355 &num_chars);
356
357 if (num_chars == strlen(&line[k])) {
358 // Modulation parsed here, not via old xine-parsing path.
359 mod[0] = '\0';
360 // It's a VDR-style config line.
361 parse_vdr_par_string(vdr_par_str, ptr);
362 // Frequency in VDR-style config files is in MHz for DVB-S,
363 // and may be in MHz, kHz or Hz for DVB-C and DVB-T.
364 // General rule to get useful units is to multiply by 1000 until value is larger than 1000000.
365 while (ptr->freq < 1000000UL) {
366 ptr->freq *= 1000UL;
367 }
368 // Symbol rate in VDR-style config files is divided by 1000.
369 ptr->srate *= 1000UL;
370 switch (delsys) {
371 case SYS_DVBT:
372 case SYS_DVBT2:
373 /* Fix delsys value. */
374 if (ptr->is_dvb_x2) {
375 ptr->delsys = delsys = SYS_DVBT2;
376 } else {
377 ptr->delsys = delsys = SYS_DVBT;
378 }
379 if (!DELSYS_IS_SET(delsys_mask, delsys))
380 continue; /* Skip channel. */
381 mp_verbose(log, "VDR, %s, NUM: %d, NUM_FIELDS: %d, NAME: %s, "
382 "FREQ: %d, SRATE: %d, T2: %s",
383 get_dvb_delsys(delsys),
384 list->NUM_CHANNELS, fields,
385 ptr->name, ptr->freq, ptr->srate,
386 (delsys == SYS_DVBT2) ? "yes" : "no");
387 break;
388 case SYS_DVBC_ANNEX_A:
389 case SYS_DVBC_ANNEX_C:
390 case SYS_ATSC:
391 case SYS_DVBC_ANNEX_B:
392 mp_verbose(log, "VDR, %s, NUM: %d, NUM_FIELDS: %d, NAME: %s, "
393 "FREQ: %d, SRATE: %d",
394 get_dvb_delsys(delsys),
395 list->NUM_CHANNELS, fields,
396 ptr->name, ptr->freq, ptr->srate);
397 break;
398 case SYS_DVBS:
399 case SYS_DVBS2:
400 /* Fix delsys value. */
401 if (ptr->is_dvb_x2) {
402 ptr->delsys = delsys = SYS_DVBS2;
403 } else {
404 ptr->delsys = delsys = SYS_DVBS;
405 }
406 if (!DELSYS_IS_SET(delsys_mask, delsys))
407 continue; /* Skip channel. */
408
409 if (vdr_loc_str[0]) {
410 // In older vdr config format, this field contained the DISEQc information.
411 // If it is numeric, assume that's it.
412 int diseqc_info = 0;
413 int valid_digits = 0;
414 if (sscanf(vdr_loc_str, "%d%n", &diseqc_info,
415 &valid_digits) == 1)
416 {
417 if (valid_digits == strlen(vdr_loc_str)) {
418 ptr->diseqc = (unsigned int)diseqc_info;
419 if (ptr->diseqc > 4)
420 continue;
421 if (ptr->diseqc > 0)
422 ptr->diseqc--;
423 }
424 }
425 }
426
427 mp_verbose(log, "VDR, %s, NUM: %d, NUM_FIELDS: %d, NAME: %s, "
428 "FREQ: %d, SRATE: %d, POL: %c, DISEQC: %d, S2: %s, "
429 "StreamID: %d, SID: %d",
430 get_dvb_delsys(delsys),
431 list->NUM_CHANNELS,
432 fields, ptr->name, ptr->freq, ptr->srate, ptr->pol,
433 ptr->diseqc, (delsys == SYS_DVBS2) ? "yes" : "no",
434 ptr->stream_id, ptr->service_id);
435 break;
436 default:
437 break;
438 }
439 } else {
440 switch (delsys) {
441 case SYS_DVBT:
442 case SYS_DVBT2:
443 fields = sscanf(&line[k], ter_conf,
444 &ptr->freq, inv, bw, cr, tmp_lcr, mod,
445 transm, gi, tmp_hier, vpid_str, apid_str);
446 mp_verbose(log, "%s, NUM: %d, NUM_FIELDS: %d, NAME: %s, FREQ: %d",
447 get_dvb_delsys(delsys), list->NUM_CHANNELS,
448 fields, ptr->name, ptr->freq);
449 break;
450 case SYS_DVBC_ANNEX_A:
451 case SYS_DVBC_ANNEX_C:
452 fields = sscanf(&line[k], cbl_conf,
453 &ptr->freq, inv, &ptr->srate,
454 cr, mod, vpid_str, apid_str);
455 mp_verbose(log, "%s, NUM: %d, NUM_FIELDS: %d, NAME: %s, FREQ: %d, "
456 "SRATE: %d",
457 get_dvb_delsys(delsys),
458 list->NUM_CHANNELS, fields, ptr->name,
459 ptr->freq, ptr->srate);
460 break;
461 #ifdef DVB_ATSC
462 case SYS_ATSC:
463 case SYS_DVBC_ANNEX_B:
464 fields = sscanf(&line[k], atsc_conf,
465 &ptr->freq, mod, vpid_str, apid_str);
466 mp_verbose(log, "%s, NUM: %d, NUM_FIELDS: %d, NAME: %s, FREQ: %d\n",
467 get_dvb_delsys(delsys), list->NUM_CHANNELS,
468 fields, ptr->name, ptr->freq);
469 break;
470 #endif
471 case SYS_DVBS:
472 case SYS_DVBS2:
473 fields = sscanf(&line[k], sat_conf,
474 &ptr->freq, &ptr->pol, &ptr->diseqc, &ptr->srate,
475 vpid_str,
476 apid_str);
477 ptr->pol = mp_toupper(ptr->pol);
478 ptr->freq *= 1000UL;
479 ptr->srate *= 1000UL;
480 if (ptr->diseqc > 4)
481 continue;
482 if (ptr->diseqc > 0)
483 ptr->diseqc--;
484 mp_verbose(log, "%s, NUM: %d, NUM_FIELDS: %d, NAME: %s, FREQ: %d, "
485 "SRATE: %d, POL: %c, DISEQC: %d",
486 get_dvb_delsys(delsys),
487 list->NUM_CHANNELS, fields, ptr->name, ptr->freq,
488 ptr->srate, ptr->pol, ptr->diseqc);
489 break;
490 default:
491 break;
492 }
493 }
494
495 if (parse_pid_string(log, vpid_str, ptr))
496 fields++;
497 if (parse_pid_string(log, apid_str, ptr))
498 fields++;
499 /* If we do not know the service_id, PMT can not be extracted.
500 Teletext decoding will fail without PMT. */
501 if (ptr->service_id != -1) {
502 if (parse_pid_string(log, tpid_str, ptr))
503 fields++;
504 }
505
506
507 if (fields < 2 || ptr->pids_cnt == 0 || ptr->freq == 0 ||
508 strlen(ptr->name) == 0)
509 continue;
510
511 /* Add some PIDs which are mandatory in DVB,
512 * and contain human-readable helpful data. */
513
514 /* This is the STD, the service description table.
515 * It contains service names and such, ffmpeg decodes it. */
516 ptr->pids[ptr->pids_cnt] = 0x0011;
517 ptr->pids_cnt++;
518
519 /* This is the EIT, which contains EPG data.
520 * ffmpeg can not decode it (yet), but e.g. VLC
521 * shows what was recorded. */
522 ptr->pids[ptr->pids_cnt] = 0x0012;
523 ptr->pids_cnt++;
524
525 if (ptr->service_id != -1) {
526 /* We have the PMT-PID in addition.
527 This will be found later, when we tune to the channel.
528 Push back here to create the additional demux. */
529 ptr->pids[ptr->pids_cnt] = -1; // Placeholder.
530 ptr->pids_cnt++;
531 }
532
533 has8192 = has0 = 0;
534 for (cnt = 0; cnt < ptr->pids_cnt; cnt++) {
535 if (ptr->pids[cnt] == 8192)
536 has8192 = 1;
537 if (ptr->pids[cnt] == 0)
538 has0 = 1;
539 }
540
541 /* 8192 is the pseudo-PID for full TP dump,
542 enforce that if requested. */
543 if (!has8192 && cfg_full_transponder)
544 has8192 = 1;
545 if (has8192) {
546 ptr->pids[0] = 8192;
547 ptr->pids_cnt = 1;
548 } else if (!has0) {
549 ptr->pids[ptr->pids_cnt] = 0; //PID 0 is the PAT
550 ptr->pids_cnt++;
551 }
552
553 mp_verbose(log, " PIDS: ");
554 for (cnt = 0; cnt < ptr->pids_cnt; cnt++)
555 mp_verbose(log, " %d ", ptr->pids[cnt]);
556 mp_verbose(log, "\n");
557
558 switch (delsys) {
559 case SYS_DVBT:
560 case SYS_DVBT2:
561 case SYS_DVBC_ANNEX_A:
562 case SYS_DVBC_ANNEX_C:
563 if (!strcmp(inv, "INVERSION_ON")) {
564 ptr->inv = INVERSION_ON;
565 } else if (!strcmp(inv, "INVERSION_OFF")) {
566 ptr->inv = INVERSION_OFF;
567 }
568
569
570 if (!strcmp(cr, "FEC_1_2")) {
571 ptr->cr = FEC_1_2;
572 } else if (!strcmp(cr, "FEC_2_3")) {
573 ptr->cr = FEC_2_3;
574 } else if (!strcmp(cr, "FEC_3_4")) {
575 ptr->cr = FEC_3_4;
576 } else if (!strcmp(cr, "FEC_4_5")) {
577 ptr->cr = FEC_4_5;
578 } else if (!strcmp(cr, "FEC_6_7")) {
579 ptr->cr = FEC_6_7;
580 } else if (!strcmp(cr, "FEC_8_9")) {
581 ptr->cr = FEC_8_9;
582 } else if (!strcmp(cr, "FEC_5_6")) {
583 ptr->cr = FEC_5_6;
584 } else if (!strcmp(cr, "FEC_7_8")) {
585 ptr->cr = FEC_7_8;
586 } else if (!strcmp(cr, "FEC_NONE")) {
587 ptr->cr = FEC_NONE;
588 }
589 }
590
591 switch (delsys) {
592 case SYS_DVBT:
593 case SYS_DVBT2:
594 case SYS_DVBC_ANNEX_A:
595 case SYS_DVBC_ANNEX_C:
596 case SYS_ATSC:
597 case SYS_DVBC_ANNEX_B:
598 if (!strcmp(mod, "QAM_128")) {
599 ptr->mod = QAM_128;
600 } else if (!strcmp(mod, "QAM_256")) {
601 ptr->mod = QAM_256;
602 } else if (!strcmp(mod, "QAM_64")) {
603 ptr->mod = QAM_64;
604 } else if (!strcmp(mod, "QAM_32")) {
605 ptr->mod = QAM_32;
606 } else if (!strcmp(mod, "QAM_16")) {
607 ptr->mod = QAM_16;
608 #ifdef DVB_ATSC
609 } else if (!strcmp(mod, "VSB_8") || !strcmp(mod, "8VSB")) {
610 ptr->mod = VSB_8;
611 } else if (!strcmp(mod, "VSB_16") || !strcmp(mod, "16VSB")) {
612 ptr->mod = VSB_16;
613 #endif
614 }
615 }
616 #ifdef DVB_ATSC
617 /* Modulation defines real delsys for ATSC:
618 Terrestrial (VSB) is SYS_ATSC, Cable (QAM) is SYS_DVBC_ANNEX_B. */
619 if (delsys == SYS_ATSC || delsys == SYS_DVBC_ANNEX_B) {
620 if (ptr->mod == VSB_8 || ptr->mod == VSB_16) {
621 delsys = SYS_ATSC;
622 } else {
623 delsys = SYS_DVBC_ANNEX_B;
624 }
625 if (!DELSYS_IS_SET(delsys_mask, delsys))
626 continue; /* Skip channel. */
627 mp_verbose(log, "Switched to delivery system for ATSC: %s (guessed from modulation).\n",
628 get_dvb_delsys(delsys));
629 }
630 #endif
631
632 switch (delsys) {
633 case SYS_DVBT:
634 case SYS_DVBT2:
635 if (!strcmp(bw, "BANDWIDTH_5_MHZ")) {
636 ptr->bw = BANDWIDTH_5_MHZ;
637 } else if (!strcmp(bw, "BANDWIDTH_6_MHZ")) {
638 ptr->bw = BANDWIDTH_6_MHZ;
639 } else if (!strcmp(bw, "BANDWIDTH_7_MHZ")) {
640 ptr->bw = BANDWIDTH_7_MHZ;
641 } else if (!strcmp(bw, "BANDWIDTH_8_MHZ")) {
642 ptr->bw = BANDWIDTH_8_MHZ;
643 } else if (!strcmp(bw, "BANDWIDTH_10_MHZ")) {
644 ptr->bw = BANDWIDTH_10_MHZ;
645 }
646
647
648 if (!strcmp(transm, "TRANSMISSION_MODE_2K")) {
649 ptr->trans = TRANSMISSION_MODE_2K;
650 } else if (!strcmp(transm, "TRANSMISSION_MODE_8K")) {
651 ptr->trans = TRANSMISSION_MODE_8K;
652 } else if (!strcmp(transm, "TRANSMISSION_MODE_AUTO")) {
653 ptr->trans = TRANSMISSION_MODE_AUTO;
654 }
655
656 if (!strcmp(gi, "GUARD_INTERVAL_1_32")) {
657 ptr->gi = GUARD_INTERVAL_1_32;
658 } else if (!strcmp(gi, "GUARD_INTERVAL_1_16")) {
659 ptr->gi = GUARD_INTERVAL_1_16;
660 } else if (!strcmp(gi, "GUARD_INTERVAL_1_8")) {
661 ptr->gi = GUARD_INTERVAL_1_8;
662 } else if (!strcmp(gi, "GUARD_INTERVAL_1_4")) {
663 ptr->gi = GUARD_INTERVAL_1_4;
664 }
665
666 if (!strcmp(tmp_lcr, "FEC_1_2")) {
667 ptr->cr_lp = FEC_1_2;
668 } else if (!strcmp(tmp_lcr, "FEC_2_3")) {
669 ptr->cr_lp = FEC_2_3;
670 } else if (!strcmp(tmp_lcr, "FEC_3_4")) {
671 ptr->cr_lp = FEC_3_4;
672 } else if (!strcmp(tmp_lcr, "FEC_4_5")) {
673 ptr->cr_lp = FEC_4_5;
674 } else if (!strcmp(tmp_lcr, "FEC_6_7")) {
675 ptr->cr_lp = FEC_6_7;
676 } else if (!strcmp(tmp_lcr, "FEC_8_9")) {
677 ptr->cr_lp = FEC_8_9;
678 } else if (!strcmp(tmp_lcr, "FEC_5_6")) {
679 ptr->cr_lp = FEC_5_6;
680 } else if (!strcmp(tmp_lcr, "FEC_7_8")) {
681 ptr->cr_lp = FEC_7_8;
682 } else if (!strcmp(tmp_lcr, "FEC_NONE")) {
683 ptr->cr_lp = FEC_NONE;
684 }
685
686
687 if (!strcmp(tmp_hier, "HIERARCHY_1")) {
688 ptr->hier = HIERARCHY_1;
689 } else if (!strcmp(tmp_hier, "HIERARCHY_2")) {
690 ptr->hier = HIERARCHY_2;
691 } else if (!strcmp(tmp_hier, "HIERARCHY_4")) {
692 ptr->hier = HIERARCHY_4;
693 } else if (!strcmp(tmp_hier, "HIERARCHY_NONE")) {
694 ptr->hier = HIERARCHY_NONE;
695 }
696 }
697
698 tmp = realloc(list->channels, sizeof(dvb_channel_t) *
699 (list->NUM_CHANNELS + 1));
700 if (tmp == NULL)
701 break;
702
703 list->channels = tmp;
704 memcpy(&(list->channels[list->NUM_CHANNELS]), ptr, sizeof(dvb_channel_t));
705 list->NUM_CHANNELS++;
706 if (sizeof(dvb_channel_t) * list->NUM_CHANNELS >= 1024 * 1024) {
707 mp_verbose(log, "dvbin.c, > 1MB allocated for channels struct, "
708 "dropping the rest of the file\n");
709 break;
710 }
711 }
712
713 fclose(f);
714 if (list->NUM_CHANNELS == 0) {
715 free(list->channels);
716 free(list);
717 return NULL;
718 }
719
720 return list;
721 }
722
dvb_free_state(dvb_state_t * state)723 void dvb_free_state(dvb_state_t *state)
724 {
725 int i, j;
726
727 for (i = 0; i < state->adapters_count; i++) {
728 if (!state->adapters[i].list)
729 continue;
730 if (state->adapters[i].list->channels) {
731 for (j = 0; j < state->adapters[i].list->NUM_CHANNELS; j++)
732 free(state->adapters[i].list->channels[j].name);
733 free(state->adapters[i].list->channels);
734 }
735 free(state->adapters[i].list);
736 }
737 free(state);
738 }
739
dvb_streaming_read(stream_t * stream,void * buffer,int size)740 static int dvb_streaming_read(stream_t *stream, void *buffer, int size)
741 {
742 struct pollfd pfds[1];
743 int pos = 0, tries, rk, fd;
744 dvb_priv_t *priv = (dvb_priv_t *) stream->priv;
745 dvb_state_t *state = priv->state;
746
747 MP_TRACE(stream, "dvb_streaming_read(%d)\n", size);
748
749 tries = state->retry;
750 fd = state->dvr_fd;
751 while (pos < size) {
752 rk = read(fd, (char *)buffer + pos, (size - pos));
753 if (rk <= 0) {
754 if (pos || tries == 0)
755 break;
756 tries --;
757 pfds[0].fd = fd;
758 pfds[0].events = POLLIN | POLLPRI;
759 if (poll(pfds, 1, 2000) <= 0) {
760 MP_ERR(stream, "dvb_streaming_read, failed with "
761 "errno %d when reading %d bytes\n", errno, size - pos);
762 errno = 0;
763 break;
764 }
765 continue;
766 }
767 pos += rk;
768 MP_TRACE(stream, "ret (%d) bytes\n", pos);
769 }
770
771 if (!pos)
772 MP_ERR(stream, "dvb_streaming_read, return 0 bytes\n");
773
774 // Check if config parameters have been updated.
775 dvb_update_config(stream);
776
777 return pos;
778 }
779
dvb_set_channel(stream_t * stream,unsigned int adapter,unsigned int n)780 int dvb_set_channel(stream_t *stream, unsigned int adapter, unsigned int n)
781 {
782 dvb_channels_list_t *new_list;
783 dvb_channel_t *channel;
784 dvb_priv_t *priv = stream->priv;
785 char buf[4096];
786 dvb_state_t *state = (dvb_state_t *) priv->state;
787 int devno;
788 int i;
789
790 if (adapter >= state->adapters_count) {
791 MP_ERR(stream, "dvb_set_channel: INVALID internal ADAPTER NUMBER: %d vs %d, abort\n",
792 adapter, state->adapters_count);
793 return 0;
794 }
795
796 devno = state->adapters[adapter].devno;
797 new_list = state->adapters[adapter].list;
798 if (n > new_list->NUM_CHANNELS) {
799 MP_ERR(stream, "dvb_set_channel: INVALID CHANNEL NUMBER: %d, for "
800 "adapter %d, abort\n", n, devno);
801 return 0;
802 }
803 channel = &(new_list->channels[n]);
804
805 if (state->is_on) { //the fds are already open and we have to stop the demuxers
806 /* Remove all demuxes. */
807 dvb_fix_demuxes(priv, 0);
808
809 state->retry = 0;
810 //empty both the stream's and driver's buffer
811 while (dvb_streaming_read(stream, buf, sizeof(buf)) > 0) {}
812 if (state->cur_adapter != adapter ||
813 state->cur_frontend != channel->frontend) {
814 dvbin_close(stream);
815 if (!dvb_open_devices(priv, devno, channel->frontend, channel->pids_cnt)) {
816 MP_ERR(stream, "DVB_SET_CHANNEL, COULDN'T OPEN DEVICES OF "
817 "ADAPTER: %d, EXIT\n", devno);
818 return 0;
819 }
820 } else {
821 // close all demux_fds with pos > pids required for the new channel
822 // or open other demux_fds if we have too few
823 if (!dvb_fix_demuxes(priv, channel->pids_cnt))
824 return 0;
825 }
826 } else {
827 if (!dvb_open_devices(priv, devno, channel->frontend, channel->pids_cnt)) {
828 MP_ERR(stream, "DVB_SET_CHANNEL2, COULDN'T OPEN DEVICES OF "
829 "ADAPTER: %d, EXIT\n", devno);
830 return 0;
831 }
832 }
833
834 state->retry = 5;
835 new_list->current = n;
836 MP_VERBOSE(stream, "DVB_SET_CHANNEL: new channel name=%s, adapter: %d, "
837 "channel %d\n", channel->name, devno, n);
838
839 if (channel->freq != state->last_freq) {
840 if (!dvb_tune(priv, channel->delsys, channel->freq,
841 channel->pol, channel->srate, channel->diseqc,
842 channel->stream_id, channel->inv,
843 channel->mod, channel->gi,
844 channel->trans, channel->bw, channel->cr, channel->cr_lp,
845 channel->hier, priv->opts->cfg_timeout))
846 return 0;
847 }
848
849 state->is_on = 1;
850 state->last_freq = channel->freq;
851 state->cur_adapter = adapter;
852 state->cur_frontend = channel->frontend;
853
854 if (channel->service_id != -1) {
855 /* We need the PMT-PID in addition.
856 If it has not yet beem resolved, do it now. */
857 for (i = 0; i < channel->pids_cnt; i++) {
858 if (channel->pids[i] == -1) {
859 MP_VERBOSE(stream, "DVB_SET_CHANNEL: PMT-PID for service %d "
860 "not resolved yet, parsing PAT...\n",
861 channel->service_id);
862 int pmt_pid = dvb_get_pmt_pid(priv, adapter, channel->service_id);
863 MP_VERBOSE(stream, "DVB_SET_CHANNEL: Found PMT-PID: %d\n",
864 pmt_pid);
865 channel->pids[i] = pmt_pid;
866 }
867 }
868 }
869
870 // sets demux filters and restart the stream
871 for (i = 0; i < channel->pids_cnt; i++) {
872 if (channel->pids[i] == -1) {
873 // In case PMT was not resolved, skip it here.
874 MP_ERR(stream, "DVB_SET_CHANNEL: PMT-PID not found, "
875 "teletext-decoding may fail.\n");
876 } else {
877 if (!dvb_set_ts_filt(priv, state->demux_fds[i], channel->pids[i],
878 DMX_PES_OTHER))
879 return 0;
880 }
881 }
882
883 return 1;
884 }
885
dvbin_stream_control(struct stream * s,int cmd,void * arg)886 static int dvbin_stream_control(struct stream *s, int cmd, void *arg)
887 {
888 dvb_priv_t *priv = (dvb_priv_t *) s->priv;
889 dvb_state_t *state = priv->state;
890 dvb_channels_list_t *list = NULL;
891
892 if (state->cur_adapter >= state->adapters_count)
893 return STREAM_ERROR;
894 list = state->adapters[state->cur_adapter].list;
895
896 switch (cmd) {
897 case STREAM_CTRL_GET_METADATA: {
898 struct mp_tags *metadata = talloc_zero(NULL, struct mp_tags);
899 char *progname = list->channels[list->current].name;
900 mp_tags_set_str(metadata, "title", progname);
901 *(struct mp_tags **)arg = metadata;
902 return STREAM_OK;
903 }
904 }
905 return STREAM_UNSUPPORTED;
906 }
907
dvbin_close(stream_t * stream)908 void dvbin_close(stream_t *stream)
909 {
910 dvb_priv_t *priv = (dvb_priv_t *) stream->priv;
911 dvb_state_t *state = priv->state;
912
913 if (state->switching_channel && state->is_on) {
914 // Prevent state destruction, reset channel-switch.
915 state->switching_channel = false;
916 pthread_mutex_lock(&global_dvb_state_lock);
917 global_dvb_state->stream_used = false;
918 pthread_mutex_unlock(&global_dvb_state_lock);
919 return;
920 }
921
922 for (int i = state->demux_fds_cnt - 1; i >= 0; i--) {
923 state->demux_fds_cnt--;
924 MP_VERBOSE(stream, "DVBIN_CLOSE, close(%d), fd=%d, COUNT=%d\n", i,
925 state->demux_fds[i], state->demux_fds_cnt);
926 close(state->demux_fds[i]);
927 }
928 close(state->dvr_fd);
929 close(state->fe_fd);
930 state->fe_fd = state->dvr_fd = -1;
931
932 state->is_on = 0;
933 state->cur_adapter = -1;
934 state->cur_frontend = -1;
935
936 pthread_mutex_lock(&global_dvb_state_lock);
937 dvb_free_state(state);
938 global_dvb_state = NULL;
939 pthread_mutex_unlock(&global_dvb_state_lock);
940 }
941
dvb_streaming_start(stream_t * stream,char * progname)942 static int dvb_streaming_start(stream_t *stream, char *progname)
943 {
944 int i;
945 dvb_channel_t *channel = NULL;
946 dvb_priv_t *priv = stream->priv;
947 dvb_state_t *state = priv->state;
948 dvb_channels_list_t *list;
949
950 if (progname == NULL)
951 return 0;
952 MP_VERBOSE(stream, "\r\ndvb_streaming_start(PROG: %s, ADAPTER: %d)\n",
953 progname, priv->devno);
954
955 list = state->adapters[state->cur_adapter].list;
956 for (i = 0; i < list->NUM_CHANNELS; i ++) {
957 if (!strcmp(list->channels[i].name, progname)) {
958 channel = &(list->channels[i]);
959 break;
960 }
961 }
962
963 if (channel == NULL) {
964 MP_ERR(stream, "\n\nDVBIN: no such channel \"%s\"\n\n", progname);
965 return 0;
966 }
967
968 list->current = i;
969
970 // When switching channels, cfg_channel_switch_offset
971 // keeps the offset to the initially chosen channel.
972 list->current = (list->NUM_CHANNELS + list->current + priv->opts->cfg_channel_switch_offset) % list->NUM_CHANNELS;
973 channel = &(list->channels[list->current]);
974 MP_INFO(stream, "Tuning to channel \"%s\"...\n", channel->name);
975 MP_VERBOSE(stream, "PROGRAM NUMBER %d: name=%s, freq=%u\n", i,
976 channel->name, channel->freq);
977
978 if (!dvb_set_channel(stream, state->cur_adapter, list->current)) {
979 MP_ERR(stream, "ERROR, COULDN'T SET CHANNEL %i: \"%s\"\n", list->current, progname);
980 dvbin_close(stream);
981 return 0;
982 }
983
984 MP_VERBOSE(stream, "SUCCESSFUL EXIT from dvb_streaming_start\n");
985
986 return 1;
987 }
988
dvb_update_config(stream_t * stream)989 void dvb_update_config(stream_t *stream)
990 {
991 static int last_check = 0;
992 int now = (int)(mp_time_sec()*10);
993
994 // Throttle the check to at maximum once every 0.1 s.
995 if (now != last_check) {
996 last_check = now;
997 dvb_priv_t *priv = (dvb_priv_t *) stream->priv;
998 if (m_config_cache_update(priv->opts_cache)) {
999 dvb_state_t *state = priv->state;
1000
1001 // Re-parse stream path, if we have cfg parameters now,
1002 // these should be preferred.
1003 if (!dvb_parse_path(stream)) {
1004 MP_ERR(stream, "error parsing DVB config, not tuning.");
1005 return;
1006 }
1007
1008 int r = dvb_streaming_start(stream, priv->prog);
1009 if (r) {
1010 // Stream will be pulled down after channel switch,
1011 // persist state.
1012 state->switching_channel = true;
1013 }
1014 }
1015 }
1016 }
1017
dvb_open(stream_t * stream)1018 static int dvb_open(stream_t *stream)
1019 {
1020 // I don't force the file format because, although it's almost always TS,
1021 // there are some providers that stream an IP multicast with M$ Mpeg4 inside
1022 dvb_priv_t *priv = NULL;
1023
1024 pthread_mutex_lock(&global_dvb_state_lock);
1025 if (global_dvb_state && global_dvb_state->stream_used) {
1026 MP_ERR(stream, "DVB stream already in use, only one DVB stream can exist at a time!\n");
1027 pthread_mutex_unlock(&global_dvb_state_lock);
1028 goto err_out;
1029 }
1030
1031 // Need to re-get config in any case, not part of global state.
1032 stream->priv = talloc_zero(stream, dvb_priv_t);
1033 priv = stream->priv;
1034 priv->opts_cache = m_config_cache_alloc(stream, stream->global, &stream_dvb_conf);
1035 priv->opts = priv->opts_cache->opts;
1036
1037 dvb_state_t *state = dvb_get_state(stream);
1038
1039 priv->state = state;
1040 priv->log = stream->log;
1041 if (state == NULL) {
1042 MP_ERR(stream, "DVB CONFIGURATION IS EMPTY, exit\n");
1043 pthread_mutex_unlock(&global_dvb_state_lock);
1044 goto err_out;
1045 }
1046
1047 if (!dvb_parse_path(stream)) {
1048 goto err_out;
1049 }
1050
1051 state->stream_used = true;
1052 pthread_mutex_unlock(&global_dvb_state_lock);
1053
1054 if (state->is_on != 1) {
1055 // State could be already initialized, for example, we just did a channel switch.
1056 // The following setup only has to be done once.
1057
1058 state->cur_frontend = -1;
1059
1060 MP_VERBOSE(stream, "OPEN_DVB: prog=%s, devno=%d\n",
1061 priv->prog, state->adapters[state->cur_adapter].devno);
1062
1063 if (!dvb_streaming_start(stream, priv->prog))
1064 goto err_out;
1065 }
1066
1067 stream->fill_buffer = dvb_streaming_read;
1068 stream->close = dvbin_close;
1069 stream->control = dvbin_stream_control;
1070 stream->streaming = true;
1071 stream->demuxer = "lavf";
1072 stream->lavf_type = "mpegts";
1073
1074 return STREAM_OK;
1075
1076 err_out:
1077 talloc_free(priv);
1078 stream->priv = NULL;
1079 return STREAM_ERROR;
1080 }
1081
dvb_parse_path(stream_t * stream)1082 int dvb_parse_path(stream_t *stream)
1083 {
1084 dvb_priv_t *priv = stream->priv;
1085 dvb_state_t *state = priv->state;
1086
1087 // Parse stream path. Common rule: cfg wins over stream path,
1088 // since cfg may be changed at runtime.
1089 bstr prog, devno;
1090 if (!bstr_split_tok(bstr0(stream->path), "@", &devno, &prog)) {
1091 prog = devno;
1092 devno.len = 0;
1093 }
1094
1095 if (priv->opts->cfg_devno != 0) {
1096 priv->devno = priv->opts->cfg_devno;
1097 } else if (devno.len) {
1098 bstr r;
1099 priv->devno = bstrtoll(devno, &r, 0);
1100 if (r.len || priv->devno < 0 || priv->devno >= MAX_ADAPTERS) {
1101 MP_ERR(stream, "invalid devno: '%.*s'\n", BSTR_P(devno));
1102 return 0;
1103 }
1104 } else {
1105 // Default to the default of cfg_devno.
1106 priv->devno = priv->opts->cfg_devno;
1107 }
1108
1109 // Current adapter is derived from devno.
1110 state->cur_adapter = -1;
1111 for (int i = 0; i < state->adapters_count; i++) {
1112 if (state->adapters[i].devno == priv->devno) {
1113 state->cur_adapter = i;
1114 break;
1115 }
1116 }
1117
1118 if (state->cur_adapter == -1) {
1119 MP_ERR(stream, "NO CONFIGURATION FOUND FOR ADAPTER N. %d!\n",
1120 priv->devno);
1121 return 0;
1122 }
1123
1124 if (priv->opts->cfg_prog != NULL && strlen(priv->opts->cfg_prog) > 0) {
1125 talloc_free(priv->prog);
1126 priv->prog = talloc_strdup(priv, priv->opts->cfg_prog);
1127 } else if (prog.len) {
1128 talloc_free(priv->prog);
1129 priv->prog = bstrto0(priv, prog);
1130 } else {
1131 // We use the first program from the channel list.
1132 if (state->adapters[state->cur_adapter].list == NULL) {
1133 MP_ERR(stream, "No channel list available for adapter %d!\n", priv->devno);
1134 return 0;
1135 }
1136 talloc_free(priv->prog);
1137 priv->prog = talloc_strdup(priv, state->adapters[state->cur_adapter].list->channels[0].name);
1138 }
1139
1140 MP_VERBOSE(stream, "DVB_CONFIG: prog=%s, devno=%d\n",
1141 priv->prog, priv->devno);
1142 return 1;
1143 }
1144
dvb_get_state(stream_t * stream)1145 dvb_state_t *dvb_get_state(stream_t *stream)
1146 {
1147 if (global_dvb_state != NULL) {
1148 return global_dvb_state;
1149 }
1150 struct mp_log *log = stream->log;
1151 struct mpv_global *global = stream->global;
1152 dvb_priv_t *priv = stream->priv;
1153 unsigned int delsys, delsys_mask[MAX_FRONTENDS], size;
1154 char filename[PATH_MAX], *conf_file;
1155 const char *conf_file_name;
1156 void *talloc_ctx;
1157 dvb_channels_list_t *list;
1158 dvb_adapter_config_t *adapters = NULL, *tmp;
1159 dvb_state_t *state = NULL;
1160
1161 state = malloc(sizeof(dvb_state_t));
1162 if (state == NULL)
1163 return NULL;
1164 memset(state, 0x00, sizeof(dvb_state_t));
1165 state->switching_channel = false;
1166 state->is_on = 0;
1167 state->stream_used = true;
1168 state->fe_fd = state->dvr_fd = -1;
1169 for (unsigned int i = 0; i < MAX_ADAPTERS; i++) {
1170 list = NULL;
1171 for (unsigned int f = 0; f < MAX_FRONTENDS; f++) {
1172 snprintf(filename, sizeof(filename), "/dev/dvb/adapter%u/frontend%u", i, f);
1173 int fd = open(filename, O_RDONLY | O_NONBLOCK | O_CLOEXEC);
1174 if (fd < 0)
1175 continue;
1176
1177 mp_verbose(log, "Opened device %s, FD: %d\n", filename, fd);
1178 delsys_mask[f] = dvb_get_tuner_delsys_mask(fd, log);
1179 delsys_mask[f] &= DELSYS_SUPP_MASK; /* Filter unsupported delivery systems. */
1180 close(fd);
1181 if (delsys_mask[f] == 0) {
1182 mp_verbose(log, "Frontend device %s has no supported delivery systems.\n",
1183 filename);
1184 continue; /* Skip tuner. */
1185 }
1186 mp_verbose(log, "Frontend device %s offers some supported delivery systems.\n",
1187 filename);
1188 /* Create channel list for adapter. */
1189 for (delsys = 0; delsys < SYS_DVB__COUNT__; delsys++) {
1190 if (!DELSYS_IS_SET(delsys_mask[f], delsys))
1191 continue; /* Skip unsupported. */
1192
1193 switch (delsys) {
1194 case SYS_DVBC_ANNEX_A:
1195 case SYS_DVBC_ANNEX_C:
1196 conf_file_name = "channels.conf.cbl";
1197 break;
1198 case SYS_ATSC:
1199 conf_file_name = "channels.conf.atsc";
1200 break;
1201 case SYS_DVBT:
1202 if (DELSYS_IS_SET(delsys_mask[f], SYS_DVBT2))
1203 continue; /* Add all channels later with T2. */
1204 conf_file_name = "channels.conf.ter";
1205 break;
1206 case SYS_DVBT2:
1207 conf_file_name = "channels.conf.ter";
1208 break;
1209 case SYS_DVBS:
1210 if (DELSYS_IS_SET(delsys_mask[f], SYS_DVBS2))
1211 continue; /* Add all channels later with S2. */
1212 conf_file_name = "channels.conf.sat";
1213 break;
1214 case SYS_DVBS2:
1215 conf_file_name = "channels.conf.sat";
1216 break;
1217 default:
1218 continue;
1219 }
1220
1221 if (priv->opts->cfg_file && priv->opts->cfg_file[0]) {
1222 talloc_ctx = NULL;
1223 conf_file = priv->opts->cfg_file;
1224 } else {
1225 talloc_ctx = talloc_new(NULL);
1226 conf_file = mp_find_config_file(talloc_ctx, global, conf_file_name);
1227 if (conf_file) {
1228 mp_verbose(log, "Ignoring other channels.conf files.\n");
1229 } else {
1230 conf_file = mp_find_config_file(talloc_ctx, global,
1231 "channels.conf");
1232 }
1233 }
1234
1235 list = dvb_get_channels(log, list, priv->opts->cfg_full_transponder,
1236 conf_file, f, delsys, delsys_mask[f]);
1237 talloc_free(talloc_ctx);
1238 }
1239 }
1240 /* Add adapter with non zero channel list. */
1241 if (list == NULL)
1242 continue;
1243
1244 size = sizeof(dvb_adapter_config_t) * (state->adapters_count + 1);
1245 tmp = realloc(state->adapters, size);
1246
1247 if (tmp == NULL) {
1248 mp_err(log, "DVB_CONFIG, can't realloc %d bytes, skipping\n",
1249 size);
1250 free(list);
1251 continue;
1252 }
1253 adapters = tmp;
1254
1255 state->adapters = adapters;
1256 state->adapters[state->adapters_count].devno = i;
1257 memcpy(&state->adapters[state->adapters_count].delsys_mask,
1258 &delsys_mask, (sizeof(unsigned int) * MAX_FRONTENDS));
1259 state->adapters[state->adapters_count].list = list;
1260 state->adapters_count++;
1261 }
1262
1263 if (state->adapters_count == 0) {
1264 free(state);
1265 state = NULL;
1266 }
1267
1268 global_dvb_state = state;
1269 return state;
1270 }
1271
1272 const stream_info_t stream_info_dvb = {
1273 .name = "dvbin",
1274 .open = dvb_open,
1275 .protocols = (const char *const[]){ "dvb", NULL },
1276 .stream_origin = STREAM_ORIGIN_UNSAFE,
1277 };
1278