• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2013 - Andre Roth <neolynx@gmail.com>
3  *
4  * This program is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU Lesser General Public License as published by
6  * the Free Software Foundation version 2.1 of the License.
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11  * GNU Lesser General Public License for more details.
12  *
13  * You should have received a copy of the GNU Lesser General Public License
14  * along with this program; if not, write to the Free Software
15  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
16  * Or, point your browser to http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
17  *
18  */
19 
20 #include <libdvbv5/mpeg_pes.h>
21 #include <libdvbv5/descriptors.h>
22 #include <libdvbv5/dvb-fe.h>
23 #include <inttypes.h>
24 
25 #if __GNUC__ >= 9
26 #pragma GCC diagnostic ignored "-Waddress-of-packed-member"
27 #endif
28 
dvb_mpeg_pes_init(struct dvb_v5_fe_parms * parms,const uint8_t * buf,ssize_t buflen,uint8_t * table)29 ssize_t dvb_mpeg_pes_init(struct dvb_v5_fe_parms *parms, const uint8_t *buf, ssize_t buflen, uint8_t *table)
30 {
31 	struct dvb_mpeg_pes *pes = (struct dvb_mpeg_pes *) table;
32 	const uint8_t *p = buf;
33 	ssize_t bytes_read = 0;
34 
35 	memcpy(table, p, sizeof(struct dvb_mpeg_pes));
36 	p += sizeof(struct dvb_mpeg_pes);
37 	bytes_read += sizeof(struct dvb_mpeg_pes);
38 
39 	bswap32(pes->bitfield);
40 	bswap16(pes->length);
41 
42 	if (pes->sync != 0x000001) {
43 		dvb_logerr("mpeg pes invalid, sync 0x%06x should be 0x000001", pes->sync);
44 		return -1;
45 	}
46 
47 	if (pes->stream_id == DVB_MPEG_STREAM_PADDING) {
48 		dvb_logwarn("mpeg pes padding stream ignored");
49 	} else if (pes->stream_id == DVB_MPEG_STREAM_MAP ||
50 		   pes->stream_id == DVB_MPEG_STREAM_PRIVATE_2 ||
51 		   pes->stream_id == DVB_MPEG_STREAM_ECM ||
52 		   pes->stream_id == DVB_MPEG_STREAM_EMM ||
53 		   pes->stream_id == DVB_MPEG_STREAM_DIRECTORY ||
54 		   pes->stream_id == DVB_MPEG_STREAM_DSMCC ||
55 		   pes->stream_id == DVB_MPEG_STREAM_H222E ) {
56 		dvb_logerr("mpeg pes: unsupported stream type 0x%04x", pes->stream_id);
57 		return -2;
58 	} else {
59 		memcpy(pes->optional, p, sizeof(struct dvb_mpeg_pes_optional) -
60 					 sizeof(pes->optional->pts) -
61 					 sizeof(pes->optional->dts));
62 		p += sizeof(struct dvb_mpeg_pes_optional) -
63 		     sizeof(pes->optional->pts) -
64 		     sizeof(pes->optional->dts);
65 		bswap16(pes->optional->bitfield);
66 		pes->optional->pts = 0;
67 		pes->optional->dts = 0;
68 		if (pes->optional->PTS_DTS & 2) {
69 			struct ts_t pts;
70 			memcpy(&pts, p, sizeof(pts));
71 			p += sizeof(pts);
72 			bswap16(pts.bitfield);
73 			bswap16(pts.bitfield2);
74 			if (pts.one != 1 || pts.one1 != 1 || pts.one2 != 1)
75 				dvb_logwarn("mpeg pes: invalid pts");
76 			else {
77 				pes->optional->pts |= (uint64_t) pts.bits00;
78 				pes->optional->pts |= (uint64_t) pts.bits15 << 15;
79 				pes->optional->pts |= (uint64_t) pts.bits30 << 30;
80 			}
81 		}
82 		if (pes->optional->PTS_DTS & 1) {
83 			struct ts_t dts;
84 			memcpy(&dts, p, sizeof(dts));
85 			p += sizeof(dts);
86 			bswap16(dts.bitfield);
87 			bswap16(dts.bitfield2);
88 			pes->optional->dts |= (uint64_t) dts.bits00;
89 			pes->optional->dts |= (uint64_t) dts.bits15 << 15;
90 			pes->optional->dts |= (uint64_t) dts.bits30 << 30;
91 		}
92 		bytes_read += sizeof(struct dvb_mpeg_pes_optional);
93 	}
94 	return bytes_read;
95 }
96 
dvb_mpeg_pes_free(struct dvb_mpeg_pes * ts)97 void dvb_mpeg_pes_free(struct dvb_mpeg_pes *ts)
98 {
99 	free(ts);
100 }
101 
dvb_mpeg_pes_print(struct dvb_v5_fe_parms * parms,struct dvb_mpeg_pes * pes)102 void dvb_mpeg_pes_print(struct dvb_v5_fe_parms *parms, struct dvb_mpeg_pes *pes)
103 {
104 	dvb_loginfo("MPEG PES");
105 	dvb_loginfo(" - sync    0x%06x", pes->sync);
106 	dvb_loginfo(" - stream_id 0x%04x", pes->stream_id);
107 	dvb_loginfo(" - length      %d", pes->length);
108 	if (pes->stream_id == DVB_MPEG_STREAM_PADDING) {
109 	} else if (pes->stream_id == DVB_MPEG_STREAM_MAP ||
110 		   pes->stream_id == DVB_MPEG_STREAM_PRIVATE_2 ||
111 		   pes->stream_id == DVB_MPEG_STREAM_ECM ||
112 		   pes->stream_id == DVB_MPEG_STREAM_EMM ||
113 		   pes->stream_id == DVB_MPEG_STREAM_DIRECTORY ||
114 		   pes->stream_id == DVB_MPEG_STREAM_DSMCC ||
115 		   pes->stream_id == DVB_MPEG_STREAM_H222E ) {
116 		dvb_logwarn("  mpeg pes unsupported stream type 0x%04x", pes->stream_id);
117 	} else {
118 		dvb_loginfo("  mpeg pes optional");
119 		dvb_loginfo("   - two                      %d", pes->optional->two);
120 		dvb_loginfo("   - PES_scrambling_control   %d", pes->optional->PES_scrambling_control);
121 		dvb_loginfo("   - PES_priority             %d", pes->optional->PES_priority);
122 		dvb_loginfo("   - data_alignment_indicator %d", pes->optional->data_alignment_indicator);
123 		dvb_loginfo("   - copyright                %d", pes->optional->copyright);
124 		dvb_loginfo("   - original_or_copy         %d", pes->optional->original_or_copy);
125 		dvb_loginfo("   - PTS_DTS                  %d", pes->optional->PTS_DTS);
126 		dvb_loginfo("   - ESCR                     %d", pes->optional->ESCR);
127 		dvb_loginfo("   - ES_rate                  %d", pes->optional->ES_rate);
128 		dvb_loginfo("   - DSM_trick_mode           %d", pes->optional->DSM_trick_mode);
129 		dvb_loginfo("   - additional_copy_info     %d", pes->optional->additional_copy_info);
130 		dvb_loginfo("   - PES_CRC                  %d", pes->optional->PES_CRC);
131 		dvb_loginfo("   - PES_extension            %d", pes->optional->PES_extension);
132 		dvb_loginfo("   - length                   %d", pes->optional->length);
133 		if (pes->optional->PTS_DTS & 2)
134 			dvb_loginfo("   - pts                      %" PRIu64 " (%fs)",
135 				    pes->optional->pts, (float) pes->optional->pts / 90000.0);
136 		if (pes->optional->PTS_DTS & 1)
137 			dvb_loginfo("   - dts                      %" PRIu64 " (%fs)",
138 				    pes->optional->dts, (float) pes->optional->dts/ 90000.0);
139 	}
140 }
141