Annotation of multiplexer/global.h, revision 1.15
1.1 oskar 1: /*
2: * ISO 13818 stream multiplexer
3: * Copyright (C) 2001 Convergence Integrated Media GmbH Berlin
4: * Author: Oskar Schirmer (oskar@convergence.de)
5: */
6:
7: #include <asm/types.h>
8: #include <sys/types.h>
9: #include <sys/poll.h>
10: #include <sys/time.h>
11: #include <sys/unistd.h>
12: #include <sys/stat.h>
13: #include <unistd.h>
14: #include <fcntl.h>
15: #include <stdlib.h>
16: #include <string.h>
17: #include <errno.h>
18:
19: /* for a timing and poll profile: */
20: #if 0
21: #define DEBUG_TIMEPOLL
22: #endif
23:
1.12 oskar 24: #define PES_LOWEST_SID (0xBC)
1.15 ! oskar 25: #define NUMBER_DESCR 256
1.12 oskar 26: #define TS_PACKET_SIZE 188
27:
28: #define CRC_SIZE 4
29:
1.1 oskar 30: #define MAX_MSEC_OUTDELAY 500
31: #define MAX_MSEC_PUSHJTTR (2 * 250)
1.3 oskar 32: #define MAX_MSEC_PCRDIST (100 * 80/100)
1.1 oskar 33:
1.12 oskar 34: #define TRIGGER_MSEC_INPUT 250
35: #define TRIGGER_MSEC_OUTPUT 250
1.1 oskar 36:
37: #define MAX_DATA_COMB 512
38: #define HIGHWATER_COM 8
39:
1.12 oskar 40: #define MAX_CTRL_OUTB (1 << 16)
1.4 oskar 41: #define MAX_DATA_OUTB (MAX_CTRL_OUTB << 7)
1.1 oskar 42: #define HIGHWATER_OUT 512
1.12 oskar 43: #define MAX_WRITE_OUT (44 * TS_PACKET_SIZE)
1.1 oskar 44:
1.12 oskar 45: #define MAX_CTRL_INB (1 << 10)
1.4 oskar 46: #define MAX_DATA_INBV (MAX_CTRL_INB << 10)
47: #define MAX_DATA_INBA (MAX_CTRL_INB << 9)
48: #define MAX_DATA_INB (MAX_CTRL_INB << 9)
49: #define HIGHWATER_IN (16 * 1024)
50:
51: #define MAX_DATA_RAWB (1 << 18)
52: #define HIGHWATER_RAW (16 * 1024)
53: #define MAX_READ_IN (8 * 1024)
1.1 oskar 54:
55: #define MAX_INSTREAM 64 /* ? */
56: #define MAX_INFILE 8 /* ? */
57:
58: #define MAX_STRPERPS (1<<8)
59: #define MAX_STRPERTS (1<<13)
60:
1.13 oskar 61: #define MAX_PSI_SIZE (4096+1)
62: #define CAN_PSI_SIZE (1024+1)
63: #define MAX_PMTSTREAMS (CAN_PSI_SIZE / 4)
64:
1.1 oskar 65: #define MAX_STRPERPRG 42 /* ? */
1.13 oskar 66: #define MAX_OUTPROG 32 /* ? */
67: #define MAX_PRGFORSTR MAX_OUTPROG
1.1 oskar 68:
1.12 oskar 69: #define MAX_POLLFD (MAX_INFILE+3)
70:
1.1 oskar 71: #define ENDSTR_KILL 0
72: #define ENDSTR_CLOSE 1
73: #define ENDSTR_WAIT 2
74:
75: #define boolean __u8
76: #define FALSE 0
77: #define TRUE 1
78:
79: #define byte __u8
1.4 oskar 80: #define t_msec __s32
1.1 oskar 81:
1.7 oskar 82: /* ISO 13818 clock reference 90kHz (33 bit) with 27MHz extension (9 bit).
83: * ba33 holds the high bit of base.
84: */
1.1 oskar 85: typedef struct {
1.4 oskar 86: __u32 base;
87: __u16 ext;
1.3 oskar 88: byte ba33;
1.1 oskar 89: boolean valid;
90: } clockref;
91:
1.7 oskar 92: /* For conversion purposes, this pair of values holds a partial clock
93: * reference and an internal value in milliseconds. This is to eliminate
94: * wrapping faults without producing conversion inaccuracies.
95: */
1.1 oskar 96: typedef struct {
1.4 oskar 97: __u32 base;
98: t_msec msec;
1.3 oskar 99: } conversion_base;
1.1 oskar 100:
1.7 oskar 101: /* On reference to a controlled data buffer, this one holds the control
102: * information, mainly: index into the data buffer, length of the referenced
103: * data block. In a controlled data buffer, a data block is never split to
104: * wrap at the end of the buffer. The other fields are usage dependend.
105: */
1.1 oskar 106: typedef struct {
107: int index;
108: int length;
109: int sequence;
1.4 oskar 110: t_msec msecread;
111: t_msec msecpush;
1.3 oskar 112: clockref pcr;
1.1 oskar 113: clockref opcr;
1.4 oskar 114: byte scramble;
1.1 oskar 115: } ctrl_buffer;
116:
1.7 oskar 117: /* Control buffer */
1.1 oskar 118: typedef struct {
119: ctrl_buffer *ptr;
120: int in;
121: int out;
122: int mask;
123: } refr_ctrl;
124:
1.7 oskar 125: /* Data buffer */
1.1 oskar 126: typedef struct {
127: byte *ptr;
128: int in;
129: int out;
130: int mask;
131: } refr_data;
132:
133:
1.7 oskar 134: /* Create a new buffer, return TRUE on success, FALSE otherwise */
1.1 oskar 135: #define list_create(refr,size) \
136: ((((size) & ((size)-1)) || (size < 2)) ? \
137: warn (LERR,"List Create",EGLO,1,1,size), FALSE : \
138: ((refr).ptr = malloc((size) * sizeof(*(refr).ptr))) == NULL ? \
139: warn (LERR,"List Create",EGLO,1,2,size), FALSE : \
140: ((refr).mask = (size)-1, (refr).in = (refr).out = 0, TRUE))
141:
1.7 oskar 142: /* Release a buffer no longer used */
1.1 oskar 143: #define list_release(refr) \
144: ((refr).mask = 0, free((refr).ptr), (refr).ptr = NULL)
145:
1.12 oskar 146: /* Test on buffer emptiness */
147: #define list_empty(refr) ((refr).out == (refr).in)
148:
1.7 oskar 149: /* Compute number of free elements in buffer */
1.1 oskar 150: #define list_free(refr) \
151: (((refr).out - (refr).in - 1) & (refr).mask)
152:
1.7 oskar 153: /* Compute number of free elements up to the wrapping point, if the
154: latter is included in the free part of the buffer */
1.1 oskar 155: #define list_freeinend(refr) \
156: ((refr).mask + 1 - (refr).in)
157:
1.7 oskar 158: /* Compute number of used elements in buffer (i.e. its current size) */
1.1 oskar 159: #define list_size(refr) \
160: (((refr).in - (refr).out) & (refr).mask)
161:
1.7 oskar 162: /* Test on buffer fullness */
1.1 oskar 163: #define list_full(refr) \
164: (list_free(refr) == 0)
165:
1.12 oskar 166: /* Test on buffer partial fullness (as trigger criterium) */
167: #define list_partialfull(refr) \
168: (list_size(refr) > ((refr).mask * 3/4))
1.4 oskar 169:
1.7 oskar 170: /* Increment an index variable that points in to a buffer by a given value */
1.1 oskar 171: #define list_incr(var,refr,incr) \
172: ((var) = (((var) + (incr)) & (refr).mask))
1.12 oskar 173:
1.1 oskar 174:
1.7 oskar 175: /* Check a data byte against a mask */
1.1 oskar 176: #define marker_check(data,val,mask) \
177: (((data & mask) != val) ? \
178: warn(LWAR,"Marker bit",EGLO,2,data,mask), TRUE : FALSE)
179:
1.7 oskar 180: /* Check whether a given bit is set in a data byte */
1.1 oskar 181: #define marker_bit(data,bit) \
182: marker_check(data,1<<bit,1<<bit)
183:
184: #define mmin(a,b) ((a)<(b)?(a):(b))
185: #define mmax(a,b) ((a)<(b)?(b):(a))
186:
1.7 oskar 187: /* Allocate memory for a struct with known union usage */
1.1 oskar 188: #define unionalloc(typ,fld) \
189: (malloc (sizeof(typ)-sizeof(((typ*)0)->u)+sizeof(((typ*)0)->u.fld)))
190:
1.8 oskar 191: /* Release a chained list completely */
192: #define releasechain(typ,root) \
1.14 oskar 193: { register typ *relchn_n, *relchn_p = root; \
194: while (relchn_p != NULL) { \
195: relchn_n = relchn_p->next; free (relchn_p); relchn_p = relchn_n; \
1.8 oskar 196: } }
197:
1.10 oskar 198: /* Supported input file types */
199: typedef enum {
200: ct_packetized, /* packetized elementary stream */
201: ct_program, /* program stream */
202: ct_transport, /* transport stream */
1.11 oskar 203: number_ct
1.10 oskar 204: } content_type;
205:
206: /* stream data types, dependend on buffer contents */
207: typedef enum {
208: sd_data, /* PES packet */
209: sd_map, /* mapreference containing descriptors */
210: sd_unparsedsi, /* TS packet containing raw partial SI sections */
1.11 oskar 211: number_sd
1.10 oskar 212: } streamdata_type;
213:
1.7 oskar 214: /* Reference descriptors as these are parsed from PSI */
1.1 oskar 215: typedef struct {
216: int programnumber;
1.4 oskar 217: short sourceid;
1.1 oskar 218: byte version;
1.15 ! oskar 219: byte *elemdnew[NUMBER_DESCR];
1.1 oskar 220: } mapreference;
221:
1.7 oskar 222: /* Source TS PMT list */
1.1 oskar 223: typedef struct pmtdescr {
224: struct pmtdescr *next;
225: short pat_section;
226: byte pmt_version;
227: int programnumber;
1.4 oskar 228: short pcr_pid;
229: short pmt_pid;
230: short streams;
1.1 oskar 231: short stream[MAX_PMTSTREAMS];
232: byte streamtype[MAX_PMTSTREAMS];
1.4 oskar 233: short descrlen;
1.1 oskar 234: byte elemdescr[MAX_PSI_SIZE];
235: } pmt_descr;
236:
1.7 oskar 237: /* Automatic stream usage requests as stated via command */
1.8 oskar 238: typedef struct tsautodescr {
239: struct tsautodescr *next;
240: int sprg;
241: int tprg;
242: int ssid; /* ssid<0 when referencing a complete program */
243: int tsid;
1.1 oskar 244: } tsauto_descr;
245:
1.9 oskar 246: /* Declaration of pid ranges as being not-to-be-parsed SI */
247: typedef struct tssidescr {
248: struct tssidescr *next;
249: short pid_low;
250: short pid_high;
251: } tssi_descr;
252:
1.7 oskar 253: /* Source file */
1.1 oskar 254: typedef struct {
255: refr_data data;
1.5 oskar 256: int handle;
1.1 oskar 257: char *name;
1.5 oskar 258: int filerefnum;
1.4 oskar 259: int st_mode;
1.1 oskar 260: struct pollfd *ufds;
261: int skipped; /* undesired bytes skipped, total */
262: int payload; /* split payload used total */
263: int total; /* split total (skipped, used, wasted) */
264: int sequence; /* source counter for PES sequence */
1.11 oskar 265: short openstreams[number_sd];
1.5 oskar 266: char *append_name;
267: int append_filerefnum;
268: int append_repeatitions;
1.2 oskar 269: int repeatitions;
1.1 oskar 270: int auto_programnb;
1.5 oskar 271: boolean automatic; /* extract'o'use */
272: boolean stopfile;
1.1 oskar 273: content_type content;
274: union {
275: struct {
276: struct streamdescr *stream;
277: } pes;
278: struct {
279: struct {
280: clockref scr;
1.4 oskar 281: __u32 muxrate;
1.1 oskar 282: } ph;
283: struct {
1.4 oskar 284: __u32 ratebound;
285: byte audiobound;
286: byte videobound;
1.1 oskar 287: boolean csps_flag;
288: boolean fixed_flag;
289: boolean system_video_lock_flag;
290: boolean system_audio_lock_flag;
291: boolean packet_rate_restriction_flag;
292: short buffer_bound[MAX_STRPERPS-PES_LOWEST_SID];
293: } sh;
294: /*
295: struct {
296: } dir;
297: */
298: struct streamdescr *stream[MAX_STRPERPS];
299: } ps;
300: struct {
1.4 oskar 301: __u16 transportstreamid;
1.1 oskar 302: byte pat_version;
303: byte newpat_version;
304: pmt_descr *pat;
305: pmt_descr *newpat;
306: tsauto_descr *tsauto;
1.9 oskar 307: tssi_descr *tssi;
1.1 oskar 308: struct streamdescr *stream[MAX_STRPERTS];
309: } ts;
310: } u;
311: } file_descr;
312:
1.14 oskar 313: /* Descriptors, data and reference index list */
314: typedef struct {
1.15 ! oskar 315: byte *refx[NUMBER_DESCR];
1.14 oskar 316: byte data[MAX_PSI_SIZE];
317: } descr_descr;
318:
319: /* Stream entry in target PMT, without corresponding input stream.
320: * This is used to manually denote si streams, that are brought in
321: * via --si and have to be mentioned in PMT in some way.
322: */
323: typedef struct stumpdescr {
324: struct stumpdescr *next;
325: int program_number;
326: short pid;
327: byte stream_type;
328: descr_descr manudescr;
329: } stump_descr;
330:
1.7 oskar 331: /* Target program */
1.1 oskar 332: typedef struct {
333: int program_number;
1.4 oskar 334: short pcr_pid;
335: short pmt_pid;
1.1 oskar 336: byte pmt_conticnt;
337: byte pmt_version;
338: boolean changed;
1.4 oskar 339: short pat_section;
340: short streams;
1.1 oskar 341: struct streamdescr *stream[MAX_STRPERPRG];
1.14 oskar 342: stump_descr *stump; /* just entries in PMT, not really data streams */
1.1 oskar 343: } prog_descr;
344:
1.7 oskar 345: /* Single data or map stream */
1.1 oskar 346: typedef struct streamdescr {
347: refr_ctrl ctrl;
348: refr_data data;
1.4 oskar 349: file_descr *fdescr;
350: short sourceid; /* index into fdescr->u.xx.stream[] */
1.1 oskar 351: byte stream_id; /* elementary stream id, table 2-35, etc */
1.14 oskar 352: byte stream_type; /* table 2-29 */
1.1 oskar 353: byte version;
1.4 oskar 354: byte conticnt;
355: byte endaction;
1.14 oskar 356: descr_descr *autodescr; /* Descriptors copied from input stream */
357: descr_descr *manudescr; /* Descriptors manually added */
1.1 oskar 358: /*what if a stream is leftupper corner in one prog, but elsewhere in another?*/
1.10 oskar 359: streamdata_type streamdata;
1.1 oskar 360: union {
361: struct {
1.4 oskar 362: short pid; /* splicets: 0010..1FFE, spliceps: ...FF */
1.1 oskar 363: boolean discontinuity;
364: boolean trigger;
365: boolean mention;
366: boolean has_clockref; /* in output */
1.6 oskar 367: boolean has_opcr; /* in input */
1.14 oskar 368: struct streamdescr *mapstream;
369: t_msec next_clockref;
370: t_msec delta;
371: conversion_base conv;
372: t_msec lasttime;
1.4 oskar 373: short progs;
1.1 oskar 374: prog_descr *pdescr[MAX_PRGFORSTR];
375: } d;
376: struct {
1.4 oskar 377: t_msec msectime;
1.3 oskar 378: conversion_base conv;
1.1 oskar 379: int psi_length;
380: byte psi_data[MAX_PSI_SIZE+TS_PACKET_SIZE];
381: } m;
1.10 oskar 382: struct {
383: t_msec delta;
384: } usi;
1.1 oskar 385: } u;
386: } stream_descr;
387:
388:
389: extern boolean timed_io;
390: extern boolean accept_weird_scr;
1.4 oskar 391: extern t_msec global_delta;
392: extern t_msec psi_frequency_msec;
1.1 oskar 393: extern boolean psi_frequency_changed;
394:
1.4 oskar 395: t_msec msec_now (void);
1.3 oskar 396:
397: void cref2msec (conversion_base *b,
398: clockref c,
1.4 oskar 399: t_msec *m);
1.3 oskar 400:
401: void msec2cref (conversion_base *b,
1.4 oskar 402: t_msec m,
1.3 oskar 403: clockref *c);
1.1 oskar 404:
405: void global_init (void);
406:
407:
408: #ifdef DEBUG_TIMEPOLL
409:
410: #define max_timepoll (1024*1024)
411:
412: typedef struct {
413: struct timeval tv;
1.4 oskar 414: t_msec msec_now;
1.1 oskar 415: int usec;
416: int tmo;
417: int sr, si, so;
418: unsigned char cnt_msecnow;
419: unsigned char nfdso, nfdsi;
420: unsigned char nfdsrevent;
421: unsigned char flags;
422: } timepoll;
423: #define LTP_FLAG_DELTASHIFT 0x80
424: #define LTP_FLAG_OUTPUT 0x40
425: #define LTP_FLAG_INPUT 0x20
426: #define LTP_FLAG_SPLIT 0x10
427: #define LTP_FLAG_PROCESS 0x08
428:
429: extern timepoll logtp [max_timepoll];
430: extern long logtpc;
431: extern timepoll *ltp;
432:
433: #endif
434:
LinuxTV legacy CVS <linuxtv.org/cvs>