/src/gpac/src/odf/descriptors.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * GPAC - Multimedia Framework C SDK |
3 | | * |
4 | | * Authors: Jean Le Feuvre |
5 | | * Copyright (c) Telecom ParisTech 2000-2023 |
6 | | * All rights reserved |
7 | | * |
8 | | * This file is part of GPAC / MPEG-4 ObjectDescriptor sub-project |
9 | | * |
10 | | * GPAC is free software; you can redistribute it and/or modify |
11 | | * it under the terms of the GNU Lesser General Public License as published by |
12 | | * the Free Software Foundation; either version 2, or (at your option) |
13 | | * any later version. |
14 | | * |
15 | | * GPAC is distributed in the hope that it will be useful, |
16 | | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
17 | | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
18 | | * GNU Lesser General Public License for more details. |
19 | | * |
20 | | * You should have received a copy of the GNU Lesser General Public |
21 | | * License along with this library; see the file COPYING. If not, write to |
22 | | * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. |
23 | | * |
24 | | */ |
25 | | |
26 | | #include <gpac/internal/odf_dev.h> |
27 | | #include <gpac/constants.h> |
28 | | |
29 | | #include <gpac/avparse.h> |
30 | | |
31 | | #ifndef GPAC_DISABLE_AV_PARSERS |
32 | | #include <gpac/internal/media_dev.h> |
33 | | #endif |
34 | | |
35 | | s32 gf_odf_size_field_size(u32 size_desc) |
36 | 623k | { |
37 | 623k | if (size_desc < 0x00000080) { |
38 | 622k | return 1 + 1; |
39 | 622k | } else if (size_desc < 0x00004000) { |
40 | 299 | return 2 + 1; |
41 | 500 | } else if (size_desc < 0x00200000) { |
42 | 379 | return 3 + 1; |
43 | 379 | } else if (size_desc < 0x10000000) { |
44 | 121 | return 4 + 1; |
45 | 121 | } else { |
46 | 0 | return -1; |
47 | 0 | } |
48 | | |
49 | 623k | } |
50 | | |
51 | | |
52 | | GF_EXPORT |
53 | | GF_Err gf_odf_parse_descriptor(GF_BitStream *bs, GF_Descriptor **desc, u32 *desc_size) |
54 | 325k | { |
55 | 325k | u32 val, size, sizeHeader; |
56 | 325k | u8 tag; |
57 | 325k | GF_Err err; |
58 | 325k | GF_Descriptor *newDesc; |
59 | 325k | if (!bs) return GF_BAD_PARAM; |
60 | | |
61 | 325k | *desc_size = 0; |
62 | | |
63 | | //tag |
64 | 325k | tag = (u8) gf_bs_read_int(bs, 8); |
65 | 325k | sizeHeader = 1; |
66 | | |
67 | | //size |
68 | 325k | size = 0; |
69 | 331k | do { |
70 | 331k | val = gf_bs_read_int(bs, 8); |
71 | 331k | sizeHeader++; |
72 | 331k | if (sizeHeader > 5) { |
73 | 346 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODEC, ("[ODF] Descriptor size on more than 4 bytes\n")); |
74 | 346 | return GF_ODF_INVALID_DESCRIPTOR; |
75 | 346 | } |
76 | 331k | size <<= 7; |
77 | 331k | size |= val & 0x7F; |
78 | 331k | } while ( val & 0x80); |
79 | 325k | *desc_size = size; |
80 | | |
81 | 325k | if (gf_bs_available(bs) < size) { |
82 | 4.08k | GF_LOG(GF_LOG_ERROR, GF_LOG_CODEC, ("[ODF] Not enough bytes (%d) to read descriptor (size=%d)\n", gf_bs_available(bs), size)); |
83 | 4.08k | return GF_ODF_INVALID_DESCRIPTOR; |
84 | 4.08k | } |
85 | | |
86 | 321k | GF_LOG(GF_LOG_DEBUG, GF_LOG_CODEC, ("[ODF] Reading descriptor (tag %d size %d)\n", tag, size )); |
87 | | |
88 | 321k | newDesc = gf_odf_create_descriptor(tag); |
89 | 321k | if (! newDesc) { |
90 | 873 | *desc = NULL; |
91 | 873 | *desc_size = sizeHeader; |
92 | 873 | if ( (tag >= GF_ODF_ISO_RES_BEGIN_TAG) && |
93 | 873 | (tag <= GF_ODF_ISO_RES_END_TAG) ) { |
94 | 873 | return GF_ODF_FORBIDDEN_DESCRIPTOR; |
95 | 873 | } |
96 | 0 | else if (!tag || (tag == 0xFF)) { |
97 | 0 | return GF_ODF_INVALID_DESCRIPTOR; |
98 | 0 | } |
99 | | #ifndef GPAC_MINIMAL_ODF |
100 | | return GF_OUT_OF_MEM; |
101 | | #else |
102 | 0 | gf_bs_skip_bytes(bs, size); |
103 | 0 | *desc_size = size + sizeHeader - gf_odf_size_field_size(*desc_size); |
104 | 0 | return GF_OK; |
105 | 873 | #endif |
106 | 873 | } |
107 | | |
108 | 320k | newDesc->tag = tag; |
109 | 320k | err = gf_odf_read_descriptor(bs, newDesc, *desc_size); |
110 | | |
111 | | /*FFmpeg fix*/ |
112 | 320k | if ((tag==GF_ODF_SLC_TAG) && (((GF_SLConfig*)newDesc)->predefined==2)) { |
113 | 7.97k | if (*desc_size==3) { |
114 | 319 | *desc_size = 1; |
115 | 319 | err = GF_OK; |
116 | 319 | } |
117 | 7.97k | } |
118 | | |
119 | | //little trick to handle lazy bitstreams that encode |
120 | | //SizeOfInstance on a fix number of bytes |
121 | | //This nb of bytes is added in Read methods |
122 | 320k | *desc_size += sizeHeader - gf_odf_size_field_size(*desc_size); |
123 | 320k | *desc = newDesc; |
124 | 320k | if (err) { |
125 | 22.5k | GF_LOG(GF_LOG_ERROR, GF_LOG_CODEC, ("[ODF] Error reading descriptor (tag %d size %d): %s\n", tag, size, gf_error_to_string(err) )); |
126 | 22.5k | gf_odf_delete_descriptor(newDesc); |
127 | 22.5k | *desc = NULL; |
128 | 22.5k | } |
129 | 320k | return err; |
130 | 321k | } |
131 | | |
132 | | |
133 | | |
134 | | GF_Err gf_odf_delete_descriptor_list(GF_List *descList) |
135 | 140k | { |
136 | 140k | GF_Err e; |
137 | 140k | GF_Descriptor*tmp; |
138 | 140k | u32 i; |
139 | | //no error if NULL chain... |
140 | 140k | if (! descList) return GF_OK; |
141 | 140k | i=0; |
142 | 155k | while ((tmp = (GF_Descriptor*)gf_list_enum(descList, &i))) { |
143 | 14.5k | e = gf_odf_delete_descriptor(tmp); |
144 | 14.5k | if (e) return e; |
145 | 14.5k | } |
146 | 140k | gf_list_del(descList); |
147 | 140k | return GF_OK; |
148 | 140k | } |
149 | | |
150 | | GF_Err gf_odf_write_base_descriptor(GF_BitStream *bs, u8 tag, u32 size) |
151 | 30.9k | { |
152 | 30.9k | u32 length; |
153 | 30.9k | unsigned char vals[4]; |
154 | | |
155 | 30.9k | if (!tag ) return GF_BAD_PARAM; |
156 | | |
157 | 14.4k | length = size; |
158 | 14.4k | vals[3] = (unsigned char) (length & 0x7f); |
159 | 14.4k | length >>= 7; |
160 | 14.4k | vals[2] = (unsigned char) ((length & 0x7f) | 0x80); |
161 | 14.4k | length >>= 7; |
162 | 14.4k | vals[1] = (unsigned char) ((length & 0x7f) | 0x80); |
163 | 14.4k | length >>= 7; |
164 | 14.4k | vals[0] = (unsigned char) ((length & 0x7f) | 0x80); |
165 | | |
166 | 14.4k | gf_bs_write_int(bs, tag, 8); |
167 | 14.4k | if (size < 0x00000080) { |
168 | 14.4k | gf_bs_write_int(bs, vals[3], 8); |
169 | 14.4k | } else if (size < 0x00004000) { |
170 | 1 | gf_bs_write_int(bs, vals[2], 8); |
171 | 1 | gf_bs_write_int(bs, vals[3], 8); |
172 | 1 | } else if (size < 0x00200000) { |
173 | 0 | gf_bs_write_int(bs, vals[1], 8); |
174 | 0 | gf_bs_write_int(bs, vals[2], 8); |
175 | 0 | gf_bs_write_int(bs, vals[3], 8); |
176 | 0 | } else if (size < 0x10000000) { |
177 | 0 | gf_bs_write_int(bs, vals[0], 8); |
178 | 0 | gf_bs_write_int(bs, vals[1], 8); |
179 | 0 | gf_bs_write_int(bs, vals[2], 8); |
180 | 0 | gf_bs_write_int(bs, vals[3], 8); |
181 | 0 | } else { |
182 | 0 | return GF_ODF_INVALID_DESCRIPTOR; |
183 | 0 | } |
184 | 14.4k | return GF_OK; |
185 | 14.4k | } |
186 | | |
187 | | |
188 | | GF_Err gf_odf_size_descriptor_list(GF_List *descList, u32 *outSize) |
189 | 8.96k | { |
190 | 8.96k | GF_Err e; |
191 | 8.96k | u32 tmpSize, count, i; |
192 | 8.96k | if (! descList) return GF_OK; |
193 | | |
194 | 8.96k | count = gf_list_count(descList); |
195 | 10.4k | for ( i = 0; i < count; i++ ) { |
196 | 1.52k | GF_Descriptor *tmp = (GF_Descriptor*)gf_list_get(descList, i); |
197 | 1.52k | if (tmp) { |
198 | 1.52k | e = gf_odf_size_descriptor(tmp, &tmpSize); |
199 | 1.52k | if (e) return e; |
200 | 1.52k | if (tmpSize) *outSize += tmpSize + gf_odf_size_field_size(tmpSize); |
201 | 1.52k | } |
202 | 1.52k | } |
203 | 8.96k | return GF_OK; |
204 | 8.96k | } |
205 | | |
206 | | GF_Err gf_odf_write_descriptor_list(GF_BitStream *bs, GF_List *descList) |
207 | 7.63k | { |
208 | 7.63k | GF_Err e; |
209 | 7.63k | u32 count, i; |
210 | | |
211 | 7.63k | if (! descList) return GF_OK; |
212 | 7.63k | count = gf_list_count(descList); |
213 | 8.10k | for ( i = 0; i < count; i++ ) { |
214 | 473 | GF_Descriptor *tmp = (GF_Descriptor*)gf_list_get(descList, i); |
215 | 473 | if (tmp) { |
216 | 473 | e = gf_odf_write_descriptor(bs, tmp); |
217 | 473 | if (e) return e; |
218 | 473 | } |
219 | 473 | } |
220 | 7.63k | return GF_OK; |
221 | 7.63k | } |
222 | | |
223 | | GF_Err gf_odf_write_descriptor_list_filter(GF_BitStream *bs, GF_List *descList, u8 only_tag) |
224 | 2.39k | { |
225 | 2.39k | GF_Err e; |
226 | 2.39k | u32 count, i; |
227 | | |
228 | 2.39k | if (! descList) return GF_OK; |
229 | 2.39k | count = gf_list_count(descList); |
230 | 4.49k | for ( i = 0; i < count; i++ ) { |
231 | 2.09k | GF_Descriptor *tmp = (GF_Descriptor*)gf_list_get(descList, i); |
232 | 2.09k | if (tmp && (tmp->tag==only_tag) ) { |
233 | 1.04k | e = gf_odf_write_descriptor(bs, tmp); |
234 | 1.04k | if (e) return e; |
235 | 1.04k | } |
236 | 2.09k | } |
237 | 2.39k | return GF_OK; |
238 | 2.39k | } |
239 | | |
240 | | #ifndef GPAC_MINIMAL_ODF |
241 | | |
242 | | u32 gf_ipmpx_array_size(GF_BitStream *bs, u32 *array_size) |
243 | | { |
244 | | u32 val, size, io_size; |
245 | | |
246 | | io_size = size = 0; |
247 | | do { |
248 | | val = gf_bs_read_int(bs, 8); |
249 | | io_size ++; |
250 | | size <<= 7; |
251 | | size |= val & 0x7F; |
252 | | } while ( val & 0x80 ); |
253 | | *array_size = size; |
254 | | return io_size; |
255 | | } |
256 | | |
257 | | void gf_ipmpx_write_array(GF_BitStream *bs, u8 *data, u32 data_len) |
258 | | { |
259 | | u32 length; |
260 | | unsigned char vals[4]; |
261 | | |
262 | | if (!data || !data_len) return; |
263 | | |
264 | | length = data_len; |
265 | | vals[3] = (unsigned char) (length & 0x7f); |
266 | | length >>= 7; |
267 | | vals[2] = (unsigned char) ((length & 0x7f) | 0x80); |
268 | | length >>= 7; |
269 | | vals[1] = (unsigned char) ((length & 0x7f) | 0x80); |
270 | | length >>= 7; |
271 | | vals[0] = (unsigned char) ((length & 0x7f) | 0x80); |
272 | | |
273 | | if (data_len < 0x00000080) { |
274 | | gf_bs_write_int(bs, vals[3], 8); |
275 | | } else if (data_len < 0x00004000) { |
276 | | gf_bs_write_int(bs, vals[2], 8); |
277 | | gf_bs_write_int(bs, vals[3], 8); |
278 | | } else if (data_len < 0x00200000) { |
279 | | gf_bs_write_int(bs, vals[1], 8); |
280 | | gf_bs_write_int(bs, vals[2], 8); |
281 | | gf_bs_write_int(bs, vals[3], 8); |
282 | | } else if (data_len < 0x10000000) { |
283 | | gf_bs_write_int(bs, vals[0], 8); |
284 | | gf_bs_write_int(bs, vals[1], 8); |
285 | | gf_bs_write_int(bs, vals[2], 8); |
286 | | gf_bs_write_int(bs, vals[3], 8); |
287 | | } else { |
288 | | return; |
289 | | } |
290 | | gf_bs_write_data(bs, data, data_len); |
291 | | } |
292 | | |
293 | | |
294 | | #endif /*GPAC_MINIMAL_ODF*/ |
295 | | |
296 | | /*special authoring functions*/ |
297 | | GF_EXPORT |
298 | | GF_BIFSConfig *gf_odf_get_bifs_config(GF_DefaultDescriptor *dsi, u32 oti) |
299 | 0 | { |
300 | 0 | Bool hasSize, cmd_stream; |
301 | 0 | GF_BitStream *bs; |
302 | 0 | GF_BIFSConfig *cfg; |
303 | |
|
304 | 0 | if (oti>=GF_CODECID_BIFS_EXTENDED) return NULL; |
305 | | |
306 | 0 | if (!dsi || !dsi->data || !dsi->dataLength ) { |
307 | | /* Hack for T-DMB non compliant streams (OnTimeTek ?) */ |
308 | 0 | cfg = (GF_BIFSConfig *) gf_odf_desc_new(GF_ODF_BIFS_CFG_TAG); |
309 | 0 | cfg->pixelMetrics = GF_TRUE; |
310 | 0 | cfg->version = 1; |
311 | 0 | return cfg; |
312 | 0 | } |
313 | 0 | bs = gf_bs_new(dsi->data, dsi->dataLength, GF_BITSTREAM_READ); |
314 | |
|
315 | 0 | cfg = (GF_BIFSConfig *) gf_odf_desc_new(GF_ODF_BIFS_CFG_TAG); |
316 | 0 | if (oti==2) { |
317 | | /*3D Mesh Coding*/ |
318 | 0 | gf_bs_read_int(bs, 1); |
319 | | /*PMF*/ |
320 | 0 | gf_bs_read_int(bs, 1); |
321 | 0 | } |
322 | 0 | cfg->nodeIDbits = gf_bs_read_int(bs, 5); |
323 | 0 | cfg->routeIDbits = gf_bs_read_int(bs, 5); |
324 | 0 | if (oti==2) cfg->protoIDbits = gf_bs_read_int(bs, 5); |
325 | |
|
326 | 0 | cmd_stream = (Bool)gf_bs_read_int(bs, 1); |
327 | 0 | if (!cmd_stream) { |
328 | 0 | cfg->elementaryMasks = gf_list_new(); |
329 | 0 | while (1) { |
330 | 0 | GF_ElementaryMask* em = (GF_ElementaryMask* ) gf_odf_New_ElemMask(); |
331 | 0 | em->node_id = gf_bs_read_int(bs, cfg->nodeIDbits); |
332 | 0 | gf_list_add(cfg->elementaryMasks, em); |
333 | | /*this assumes only FDP, BDP and IFS2D (no elem mask)*/ |
334 | 0 | if (gf_bs_read_int(bs, 1) == 0) break; |
335 | 0 | } |
336 | 0 | gf_bs_align(bs); |
337 | 0 | if (gf_bs_get_size(bs) != gf_bs_get_position(bs)) { |
338 | 0 | GF_LOG(GF_LOG_WARNING, GF_LOG_CODEC, ("[ODF] Reading bifs config: shift in sizes (not supported)\n")); |
339 | 0 | } |
340 | 0 | } else { |
341 | 0 | cfg->pixelMetrics = (Bool)gf_bs_read_int(bs, 1); |
342 | 0 | hasSize = (Bool)gf_bs_read_int(bs, 1); |
343 | 0 | if (hasSize) { |
344 | 0 | cfg->pixelWidth = gf_bs_read_int(bs, 16); |
345 | 0 | cfg->pixelHeight = gf_bs_read_int(bs, 16); |
346 | 0 | } |
347 | 0 | gf_bs_align(bs); |
348 | 0 | if (gf_bs_get_size(bs) != gf_bs_get_position(bs)) |
349 | 0 | GF_LOG(GF_LOG_WARNING, GF_LOG_CODEC, ("[ODF] Reading bifs config: shift in sizes (invalid descriptor)\n")); |
350 | 0 | } |
351 | 0 | gf_bs_del(bs); |
352 | 0 | return cfg; |
353 | 0 | } |
354 | | |
355 | | /*special function for authoring - convert DSI to LASERConfig*/ |
356 | | GF_EXPORT |
357 | | GF_Err gf_odf_get_laser_config(GF_DefaultDescriptor *dsi, GF_LASERConfig *cfg) |
358 | 0 | { |
359 | 0 | u32 to_skip; |
360 | 0 | GF_BitStream *bs; |
361 | |
|
362 | 0 | if (!cfg) return GF_BAD_PARAM; |
363 | 0 | memset(cfg, 0, sizeof(GF_LASERConfig)); |
364 | |
|
365 | 0 | if (!dsi || !dsi->data || !dsi->dataLength) return GF_BAD_PARAM; |
366 | 0 | bs = gf_bs_new(dsi->data, dsi->dataLength, GF_BITSTREAM_READ); |
367 | 0 | memset(cfg, 0, sizeof(GF_LASERConfig)); |
368 | 0 | cfg->tag = GF_ODF_LASER_CFG_TAG; |
369 | 0 | cfg->profile = gf_bs_read_int(bs, 8); |
370 | 0 | cfg->level = gf_bs_read_int(bs, 8); |
371 | 0 | /*cfg->reserved = */gf_bs_read_int(bs, 3); |
372 | 0 | cfg->pointsCodec = gf_bs_read_int(bs, 2); |
373 | 0 | cfg->pathComponents = gf_bs_read_int(bs, 4); |
374 | 0 | cfg->fullRequestHost = gf_bs_read_int(bs, 1); |
375 | 0 | if (gf_bs_read_int(bs, 1)) cfg->time_resolution = gf_bs_read_int(bs, 16); |
376 | 0 | else cfg->time_resolution = 1000; |
377 | 0 | cfg->colorComponentBits = 1 + gf_bs_read_int(bs, 4); |
378 | 0 | cfg->resolution = gf_bs_read_int(bs, 4); |
379 | 0 | if (cfg->resolution>7) cfg->resolution -= 16; |
380 | 0 | cfg->coord_bits = gf_bs_read_int(bs, 5); |
381 | 0 | cfg->scale_bits_minus_coord_bits = gf_bs_read_int(bs, 4); |
382 | 0 | cfg->newSceneIndicator = gf_bs_read_int(bs, 1); |
383 | 0 | /*reserved2*/ gf_bs_read_int(bs, 3); |
384 | 0 | cfg->extensionIDBits = gf_bs_read_int(bs, 4); |
385 | | /*hasExtConfig - we just ignore it*/ |
386 | 0 | if (gf_bs_read_int(bs, 1)) { |
387 | 0 | to_skip = gf_bs_read_vluimsbf5(bs); |
388 | 0 | while (to_skip) { |
389 | 0 | gf_bs_read_int(bs, 8); |
390 | 0 | to_skip--; |
391 | 0 | } |
392 | 0 | } |
393 | | /*hasExtension - we just ignore it*/ |
394 | 0 | if (gf_bs_read_int(bs, 1)) { |
395 | 0 | to_skip = gf_bs_read_vluimsbf5(bs); |
396 | 0 | while (to_skip) { |
397 | 0 | gf_bs_read_int(bs, 8); |
398 | 0 | to_skip--; |
399 | 0 | } |
400 | 0 | } |
401 | 0 | gf_bs_del(bs); |
402 | 0 | return GF_OK; |
403 | 0 | } |
404 | | //unused |
405 | | #if 0 |
406 | | GF_Err gf_odf_get_ui_config(GF_DefaultDescriptor *dsi, GF_UIConfig *cfg) |
407 | | { |
408 | | u32 len, i; |
409 | | GF_BitStream *bs; |
410 | | if (!dsi || !dsi->data || !dsi->dataLength || !cfg) return GF_BAD_PARAM; |
411 | | memset(cfg, 0, sizeof(GF_UIConfig)); |
412 | | cfg->tag = GF_ODF_UI_CFG_TAG; |
413 | | bs = gf_bs_new(dsi->data, dsi->dataLength, GF_BITSTREAM_READ); |
414 | | len = gf_bs_read_int(bs, 8); |
415 | | cfg->deviceName = (char*)gf_malloc(sizeof(char) * (len+1)); |
416 | | for (i=0; i<len; i++) cfg->deviceName[i] = gf_bs_read_int(bs, 8); |
417 | | cfg->deviceName[i] = 0; |
418 | | |
419 | | if (!stricmp(cfg->deviceName, "StringSensor") && gf_bs_available(bs)) { |
420 | | cfg->termChar = gf_bs_read_int(bs, 8); |
421 | | cfg->delChar = gf_bs_read_int(bs, 8); |
422 | | } |
423 | | gf_bs_del(bs); |
424 | | return GF_OK; |
425 | | } |
426 | | #endif |
427 | | |
428 | | GF_EXPORT |
429 | | GF_Err gf_odf_encode_ui_config(GF_UIConfig *cfg, GF_DefaultDescriptor **out_dsi) |
430 | 0 | { |
431 | 0 | u32 i, len; |
432 | 0 | GF_BitStream *bs; |
433 | 0 | GF_DefaultDescriptor *dsi; |
434 | 0 | if (!out_dsi || (cfg->tag != GF_ODF_UI_CFG_TAG)) return GF_BAD_PARAM; |
435 | | |
436 | 0 | *out_dsi = NULL; |
437 | 0 | if (!cfg->deviceName) return GF_OK; |
438 | | |
439 | 0 | bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
440 | 0 | len = (u32) strlen(cfg->deviceName); |
441 | 0 | gf_bs_write_int(bs, len, 8); |
442 | 0 | for (i=0; i<len; i++) gf_bs_write_int(bs, cfg->deviceName[i], 8); |
443 | 0 | if (!stricmp(cfg->deviceName, "StringSensor")) { |
444 | | /*fixme - this should be UTF-8 chars*/ |
445 | 0 | if (cfg->delChar || cfg->termChar) { |
446 | 0 | gf_bs_write_int(bs, cfg->termChar, 8); |
447 | 0 | gf_bs_write_int(bs, cfg->delChar, 8); |
448 | 0 | } |
449 | 0 | } |
450 | 0 | if (cfg->ui_data) gf_bs_write_data(bs, cfg->ui_data, cfg->ui_data_length); |
451 | |
|
452 | 0 | dsi = (GF_DefaultDescriptor *) gf_odf_desc_new(GF_ODF_DSI_TAG); |
453 | 0 | gf_bs_get_content(bs, &dsi->data, &dsi->dataLength); |
454 | 0 | gf_bs_del(bs); |
455 | 0 | *out_dsi = dsi; |
456 | 0 | return GF_OK; |
457 | 0 | } |
458 | | |
459 | | |
460 | | GF_EXPORT |
461 | | GF_AVCConfig *gf_odf_avc_cfg_new() |
462 | 193k | { |
463 | 193k | GF_AVCConfig *cfg; |
464 | 193k | GF_SAFEALLOC(cfg, GF_AVCConfig); |
465 | 193k | if (!cfg) return NULL; |
466 | 193k | cfg->sequenceParameterSets = gf_list_new(); |
467 | 193k | cfg->pictureParameterSets = gf_list_new(); |
468 | 193k | cfg->AVCLevelIndication = 1; |
469 | 193k | cfg->chroma_format = 1; |
470 | 193k | cfg->chroma_bit_depth = 8; |
471 | 193k | cfg->luma_bit_depth = 8; |
472 | 193k | return cfg; |
473 | 193k | } |
474 | | |
475 | | GF_EXPORT |
476 | | void gf_odf_avc_cfg_del(GF_AVCConfig *cfg) |
477 | 193k | { |
478 | 193k | if (!cfg) return; |
479 | 218k | while (gf_list_count(cfg->sequenceParameterSets)) { |
480 | 25.1k | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(cfg->sequenceParameterSets, 0); |
481 | 25.1k | gf_list_rem(cfg->sequenceParameterSets, 0); |
482 | 25.1k | if (sl->data) gf_free(sl->data); |
483 | 25.1k | gf_free(sl); |
484 | 25.1k | } |
485 | 193k | gf_list_del(cfg->sequenceParameterSets); |
486 | 193k | cfg->sequenceParameterSets = NULL; |
487 | | |
488 | 197k | while (gf_list_count(cfg->pictureParameterSets)) { |
489 | 3.79k | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(cfg->pictureParameterSets, 0); |
490 | 3.79k | gf_list_rem(cfg->pictureParameterSets, 0); |
491 | 3.79k | if (sl->data) gf_free(sl->data); |
492 | 3.79k | gf_free(sl); |
493 | 3.79k | } |
494 | 193k | gf_list_del(cfg->pictureParameterSets); |
495 | 193k | cfg->pictureParameterSets = NULL; |
496 | | |
497 | 193k | if (cfg->sequenceParameterSetExtensions) { |
498 | 25.1k | while (gf_list_count(cfg->sequenceParameterSetExtensions)) { |
499 | 3.10k | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(cfg->sequenceParameterSetExtensions, 0); |
500 | 3.10k | gf_list_rem(cfg->sequenceParameterSetExtensions, 0); |
501 | 3.10k | if (sl->data) gf_free(sl->data); |
502 | 3.10k | gf_free(sl); |
503 | 3.10k | } |
504 | 22.0k | gf_list_del(cfg->sequenceParameterSetExtensions); |
505 | 22.0k | cfg->sequenceParameterSetExtensions = NULL; |
506 | 22.0k | } |
507 | 193k | gf_free(cfg); |
508 | 193k | } |
509 | | |
510 | | GF_EXPORT |
511 | | GF_Err gf_odf_avc_cfg_write_bs(GF_AVCConfig *cfg, GF_BitStream *bs) |
512 | 76.8k | { |
513 | 76.8k | u32 i, count; |
514 | | |
515 | 76.8k | if (!cfg) return GF_BAD_PARAM; |
516 | | |
517 | 76.8k | count = gf_list_count(cfg->sequenceParameterSets); |
518 | | |
519 | 76.8k | if (!cfg->write_annex_b) { |
520 | 76.8k | gf_bs_write_int(bs, cfg->configurationVersion, 8); |
521 | 76.8k | gf_bs_write_int(bs, cfg->AVCProfileIndication , 8); |
522 | 76.8k | gf_bs_write_int(bs, cfg->profile_compatibility, 8); |
523 | 76.8k | gf_bs_write_int(bs, cfg->AVCLevelIndication, 8); |
524 | 76.8k | gf_bs_write_int(bs, 0x3F, 6); |
525 | 76.8k | gf_bs_write_int(bs, cfg->nal_unit_size - 1, 2); |
526 | 76.8k | gf_bs_write_int(bs, 0x7, 3); |
527 | 76.8k | gf_bs_write_int(bs, count, 5); |
528 | 76.8k | } |
529 | 77.9k | for (i=0; i<count; i++) { |
530 | 1.18k | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(cfg->sequenceParameterSets, i); |
531 | 1.18k | if (!cfg->write_annex_b) { |
532 | 1.18k | gf_bs_write_u16(bs, sl->size); |
533 | 1.18k | } else { |
534 | 0 | gf_bs_write_u32(bs, 1); |
535 | 0 | } |
536 | 1.18k | gf_bs_write_data(bs, sl->data, sl->size); |
537 | 1.18k | } |
538 | 76.8k | count = gf_list_count(cfg->pictureParameterSets); |
539 | 76.8k | if (!cfg->write_annex_b) { |
540 | 76.8k | gf_bs_write_int(bs, count, 8); |
541 | 76.8k | } |
542 | 78.2k | for (i=0; i<count; i++) { |
543 | 1.46k | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(cfg->pictureParameterSets, i); |
544 | 1.46k | if (!cfg->write_annex_b) { |
545 | 1.46k | gf_bs_write_u16(bs, sl->size); |
546 | 1.46k | } else { |
547 | 0 | gf_bs_write_u32(bs, 1); |
548 | 0 | } |
549 | 1.46k | gf_bs_write_data(bs, sl->data, sl->size); |
550 | 1.46k | } |
551 | 76.8k | if (gf_avcc_use_extensions(cfg->AVCProfileIndication)) { |
552 | 72.0k | if (!cfg->write_annex_b) { |
553 | 72.0k | gf_bs_write_int(bs, 0xFF, 6); |
554 | 72.0k | gf_bs_write_int(bs, cfg->chroma_format, 2); |
555 | 72.0k | gf_bs_write_int(bs, 0xFF, 5); |
556 | 72.0k | gf_bs_write_int(bs, cfg->luma_bit_depth - 8, 3); |
557 | 72.0k | gf_bs_write_int(bs, 0xFF, 5); |
558 | 72.0k | gf_bs_write_int(bs, cfg->chroma_bit_depth - 8, 3); |
559 | 72.0k | } |
560 | 72.0k | count = cfg->sequenceParameterSetExtensions ? gf_list_count(cfg->sequenceParameterSetExtensions) : 0; |
561 | 72.0k | if (!cfg->write_annex_b) { |
562 | 72.0k | gf_bs_write_u8(bs, count); |
563 | 72.0k | } |
564 | 72.6k | for (i=0; i<count; i++) { |
565 | 633 | GF_NALUFFParam *sl = (GF_NALUFFParam *) gf_list_get(cfg->sequenceParameterSetExtensions, i); |
566 | 633 | if (!cfg->write_annex_b) { |
567 | 633 | gf_bs_write_u16(bs, sl->size); |
568 | 633 | } else { |
569 | 0 | gf_bs_write_u32(bs, 1); |
570 | 0 | } |
571 | 633 | gf_bs_write_data(bs, sl->data, sl->size); |
572 | 633 | } |
573 | 72.0k | } |
574 | 76.8k | return GF_OK; |
575 | 76.8k | } |
576 | | |
577 | | GF_EXPORT |
578 | | GF_Err gf_odf_avc_cfg_write(GF_AVCConfig *cfg, u8 **outData, u32 *outSize) |
579 | 76.8k | { |
580 | 76.8k | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
581 | 76.8k | gf_odf_avc_cfg_write_bs(cfg, bs); |
582 | 76.8k | *outSize = 0; |
583 | 76.8k | *outData = NULL; |
584 | 76.8k | gf_bs_get_content(bs, outData, outSize); |
585 | 76.8k | gf_bs_del(bs); |
586 | 76.8k | return GF_OK; |
587 | 76.8k | } |
588 | | |
589 | | GF_EXPORT |
590 | | GF_AVCConfig *gf_odf_avc_cfg_read(u8 *dsi, u32 dsi_size) |
591 | 7.91k | { |
592 | 7.91k | u32 i, count; |
593 | 7.91k | GF_AVCConfig *avcc = gf_odf_avc_cfg_new(); |
594 | 7.91k | GF_BitStream *bs = gf_bs_new(dsi, dsi_size, GF_BITSTREAM_READ); |
595 | 7.91k | avcc->configurationVersion = gf_bs_read_int(bs, 8); |
596 | 7.91k | avcc->AVCProfileIndication = gf_bs_read_int(bs, 8); |
597 | 7.91k | avcc->profile_compatibility = gf_bs_read_int(bs, 8); |
598 | 7.91k | avcc->AVCLevelIndication = gf_bs_read_int(bs, 8); |
599 | 7.91k | gf_bs_read_int(bs, 6); |
600 | 7.91k | avcc->nal_unit_size = 1 + gf_bs_read_int(bs, 2); |
601 | 7.91k | gf_bs_read_int(bs, 3); |
602 | 7.91k | count = gf_bs_read_int(bs, 5); |
603 | 7.93k | for (i=0; i<count; i++) { |
604 | 34 | GF_NALUFFParam *sl; |
605 | 34 | u32 size = gf_bs_read_int(bs, 16); |
606 | 34 | if ((size>gf_bs_available(bs)) || (size<2)) { |
607 | 6 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[AVC] Wrong param set size %d\n", size)); |
608 | 6 | gf_bs_del(bs); |
609 | 6 | gf_odf_avc_cfg_del(avcc); |
610 | 6 | return NULL; |
611 | 6 | } |
612 | 28 | GF_SAFEALLOC(sl, GF_NALUFFParam ); |
613 | 28 | if (!sl) { |
614 | 0 | gf_bs_del(bs); |
615 | 0 | gf_odf_avc_cfg_del(avcc); |
616 | 0 | return NULL; |
617 | 0 | } |
618 | 28 | sl->size = size; |
619 | 28 | sl->data = (char*)gf_malloc(sizeof(char)*sl->size); |
620 | 28 | if (!sl->data) { |
621 | 0 | gf_bs_del(bs); |
622 | 0 | gf_odf_avc_cfg_del(avcc); |
623 | 0 | return NULL; |
624 | 0 | } |
625 | 28 | gf_bs_read_data(bs, sl->data, sl->size); |
626 | 28 | gf_list_add(avcc->sequenceParameterSets, sl); |
627 | 28 | } |
628 | 7.90k | count = gf_bs_read_int(bs, 8); |
629 | 7.93k | for (i=0; i<count; i++) { |
630 | 2.08k | GF_NALUFFParam *sl; |
631 | 2.08k | u32 size = gf_bs_read_int(bs, 16); |
632 | 2.08k | if ((size>gf_bs_available(bs)) || (size<2)) { |
633 | 2.05k | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[AVC] Wrong param set size %d\n", size)); |
634 | 2.05k | gf_bs_del(bs); |
635 | 2.05k | gf_odf_avc_cfg_del(avcc); |
636 | 2.05k | return NULL; |
637 | 2.05k | } |
638 | 28 | GF_SAFEALLOC(sl, GF_NALUFFParam ); |
639 | 28 | if (!sl) { |
640 | 0 | gf_bs_del(bs); |
641 | 0 | gf_odf_avc_cfg_del(avcc); |
642 | 0 | return NULL; |
643 | 0 | } |
644 | 28 | sl->size = size; |
645 | 28 | sl->data = (char*)gf_malloc(sizeof(char)*sl->size); |
646 | 28 | if (!sl->data) { |
647 | 0 | gf_bs_del(bs); |
648 | 0 | gf_odf_avc_cfg_del(avcc); |
649 | 0 | return NULL; |
650 | 0 | } |
651 | 28 | gf_bs_read_data(bs, sl->data, sl->size); |
652 | 28 | gf_list_add(avcc->pictureParameterSets, sl); |
653 | 28 | } |
654 | 5.85k | if (gf_avcc_use_extensions(avcc->AVCProfileIndication)) { |
655 | 3.70k | gf_bs_read_int(bs, 6); |
656 | 3.70k | avcc->chroma_format = gf_bs_read_int(bs, 2); |
657 | 3.70k | gf_bs_read_int(bs, 5); |
658 | 3.70k | avcc->luma_bit_depth = 8 + gf_bs_read_int(bs, 3); |
659 | 3.70k | gf_bs_read_int(bs, 5); |
660 | 3.70k | avcc->chroma_bit_depth = 8 + gf_bs_read_int(bs, 3); |
661 | | |
662 | 3.70k | count = gf_bs_read_int(bs, 8); |
663 | 3.70k | if (count) { |
664 | 0 | avcc->sequenceParameterSetExtensions = gf_list_new(); |
665 | 0 | for (i=0; i<count; i++) { |
666 | 0 | GF_NALUFFParam *sl; |
667 | 0 | u32 size = gf_bs_read_int(bs, 16); |
668 | 0 | if ((size>gf_bs_available(bs)) || (size<2)) { |
669 | 0 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[AVC] Wrong param set size %d\n", size)); |
670 | 0 | gf_bs_del(bs); |
671 | 0 | gf_odf_avc_cfg_del(avcc); |
672 | 0 | return NULL; |
673 | 0 | } |
674 | 0 | GF_SAFEALLOC(sl, GF_NALUFFParam ); |
675 | 0 | if (!sl) { |
676 | 0 | gf_bs_del(bs); |
677 | 0 | gf_odf_avc_cfg_del(avcc); |
678 | 0 | return NULL; |
679 | 0 | } |
680 | 0 | sl->size = size; |
681 | 0 | sl->data = (char*)gf_malloc(sizeof(char)*sl->size); |
682 | 0 | if (!sl->data) { |
683 | 0 | gf_bs_del(bs); |
684 | 0 | gf_odf_avc_cfg_del(avcc); |
685 | 0 | return NULL; |
686 | 0 | } |
687 | 0 | gf_bs_read_data(bs, sl->data, sl->size); |
688 | 0 | gf_list_add(avcc->sequenceParameterSetExtensions, sl); |
689 | 0 | } |
690 | 0 | } |
691 | 3.70k | } |
692 | | |
693 | | |
694 | 5.85k | gf_bs_del(bs); |
695 | 5.85k | return avcc; |
696 | 5.85k | } |
697 | | |
698 | | |
699 | | GF_Descriptor *gf_odf_new_tx3g() |
700 | 288 | { |
701 | 288 | GF_TextSampleDescriptor *newDesc = (GF_TextSampleDescriptor*) gf_malloc(sizeof(GF_TextSampleDescriptor)); |
702 | 288 | if (!newDesc) return NULL; |
703 | 288 | memset(newDesc, 0, sizeof(GF_TextSampleDescriptor)); |
704 | 288 | newDesc->tag = GF_ODF_TX3G_TAG; |
705 | 288 | return (GF_Descriptor *) newDesc; |
706 | 288 | } |
707 | | GF_Err gf_odf_del_tx3g(GF_TextSampleDescriptor *sd) |
708 | 288 | { |
709 | 288 | u32 i; |
710 | 433 | for (i=0; i<sd->font_count; i++) |
711 | 145 | if (sd->fonts[i].fontName) gf_free(sd->fonts[i].fontName); |
712 | 288 | gf_free(sd->fonts); |
713 | 288 | gf_free(sd); |
714 | 288 | return GF_OK; |
715 | 288 | } |
716 | | |
717 | | GF_EXPORT |
718 | | GF_TextSampleDescriptor *gf_odf_tx3g_read(u8 *dsi, u32 dsi_size) |
719 | 0 | { |
720 | 0 | #ifndef GPAC_DISABLE_ISOM |
721 | 0 | u32 i; |
722 | 0 | u32 gpp_read_rgba(GF_BitStream *bs); |
723 | 0 | void gpp_read_style(GF_BitStream *bs, GF_StyleRecord *rec); |
724 | 0 | void gpp_read_box(GF_BitStream *bs, GF_BoxRecord *rec); |
725 | |
|
726 | 0 | GF_TextSampleDescriptor *txtc = (GF_TextSampleDescriptor *) gf_odf_new_tx3g(); |
727 | 0 | GF_BitStream *bs = gf_bs_new(dsi, dsi_size, GF_BITSTREAM_READ); |
728 | |
|
729 | 0 | txtc->displayFlags = gf_bs_read_int(bs, 32); |
730 | 0 | txtc->horiz_justif = gf_bs_read_int(bs, 8); |
731 | 0 | txtc->vert_justif = gf_bs_read_int(bs, 8); |
732 | 0 | txtc->back_color = gpp_read_rgba(bs); |
733 | 0 | gpp_read_box(bs, &txtc->default_pos); |
734 | 0 | gpp_read_style(bs, &txtc->default_style); |
735 | 0 | txtc->font_count = gf_bs_read_u16(bs); |
736 | 0 | txtc->fonts = gf_malloc(sizeof(GF_FontRecord)*txtc->font_count); |
737 | 0 | for (i=0; i<txtc->font_count; i++) { |
738 | 0 | u8 len; |
739 | 0 | txtc->fonts[i].fontID = gf_bs_read_u16(bs); |
740 | 0 | len = gf_bs_read_u8(bs); |
741 | 0 | txtc->fonts[i].fontName = gf_malloc(sizeof(char)*(len+1)); |
742 | 0 | gf_bs_read_data(bs, txtc->fonts[i].fontName, len); |
743 | 0 | txtc->fonts[i].fontName[len] = 0; |
744 | 0 | } |
745 | 0 | gf_bs_del(bs); |
746 | 0 | return txtc; |
747 | | #else |
748 | | return NULL; |
749 | | #endif |
750 | 0 | } |
751 | | |
752 | | GF_Err gf_odf_tx3g_write(GF_TextSampleDescriptor *a, u8 **outData, u32 *outSize) |
753 | 145 | { |
754 | 145 | #ifndef GPAC_DISABLE_ISOM |
755 | 145 | u32 j; |
756 | 145 | void gpp_write_rgba(GF_BitStream *bs, u32 col); |
757 | 145 | void gpp_write_box(GF_BitStream *bs, GF_BoxRecord *rec); |
758 | 145 | void gpp_write_style(GF_BitStream *bs, GF_StyleRecord *rec); |
759 | 145 | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
760 | | |
761 | 145 | gf_bs_write_u32(bs, a->displayFlags); |
762 | 145 | gf_bs_write_u8(bs, a->horiz_justif); |
763 | 145 | gf_bs_write_u8(bs, a->vert_justif); |
764 | 145 | gpp_write_rgba(bs, a->back_color); |
765 | 145 | gpp_write_box(bs, &a->default_pos); |
766 | 145 | gpp_write_style(bs, &a->default_style); |
767 | | |
768 | 145 | gf_bs_write_u16(bs, a->font_count); |
769 | 290 | for (j=0; j<a->font_count; j++) { |
770 | 145 | gf_bs_write_u16(bs, a->fonts[j].fontID); |
771 | 145 | if (a->fonts[j].fontName) { |
772 | 145 | u32 len = (u32) strlen(a->fonts[j].fontName); |
773 | 145 | gf_bs_write_u8(bs, len); |
774 | 145 | gf_bs_write_data(bs, a->fonts[j].fontName, len); |
775 | 145 | } else { |
776 | 0 | gf_bs_write_u8(bs, 0); |
777 | 0 | } |
778 | 145 | } |
779 | 145 | gf_bs_get_content(bs, outData, outSize); |
780 | 145 | gf_bs_del(bs); |
781 | 145 | return GF_OK; |
782 | | #else |
783 | | return GF_NOT_SUPPORTED; |
784 | | #endif |
785 | 145 | } |
786 | | |
787 | | /*TextConfig*/ |
788 | | GF_Descriptor *gf_odf_new_text_cfg() |
789 | 1.08k | { |
790 | 1.08k | GF_TextConfig *newDesc = (GF_TextConfig*) gf_malloc(sizeof(GF_TextConfig)); |
791 | 1.08k | if (!newDesc) return NULL; |
792 | 1.08k | memset(newDesc, 0, sizeof(GF_TextConfig)); |
793 | 1.08k | newDesc->tag = GF_ODF_TEXT_CFG_TAG; |
794 | 1.08k | newDesc->sample_descriptions = gf_list_new(); |
795 | 1.08k | newDesc->Base3GPPFormat = 0x10; |
796 | 1.08k | newDesc->MPEGExtendedFormat = 0x10; |
797 | 1.08k | newDesc->profileLevel = 0x10; |
798 | 1.08k | newDesc->timescale = 1000; |
799 | 1.08k | return (GF_Descriptor *) newDesc; |
800 | 1.08k | } |
801 | | |
802 | | void ResetTextConfig(GF_TextConfig *desc) |
803 | 1.08k | { |
804 | 1.08k | GF_List *bck; |
805 | 1.08k | while (gf_list_count(desc->sample_descriptions)) { |
806 | 0 | GF_TextSampleDescriptor *sd = (GF_TextSampleDescriptor *)gf_list_get(desc->sample_descriptions, 0); |
807 | 0 | gf_list_rem(desc->sample_descriptions, 0); |
808 | 0 | gf_odf_del_tx3g(sd); |
809 | 0 | } |
810 | 1.08k | bck = desc->sample_descriptions; |
811 | 1.08k | memset(desc, 0, sizeof(GF_TextConfig)); |
812 | 1.08k | desc->tag = GF_ODF_TEXT_CFG_TAG; |
813 | 1.08k | desc->sample_descriptions = bck; |
814 | 1.08k | } |
815 | | |
816 | | GF_Err gf_odf_del_text_cfg(GF_TextConfig *desc) |
817 | 1.08k | { |
818 | 1.08k | ResetTextConfig(desc); |
819 | 1.08k | gf_list_del(desc->sample_descriptions); |
820 | 1.08k | gf_free(desc); |
821 | 1.08k | return GF_OK; |
822 | 1.08k | } |
823 | | |
824 | | /*we need box parsing*/ |
825 | | #include <gpac/internal/isomedia_dev.h> |
826 | | GF_EXPORT |
827 | | GF_Err gf_odf_get_text_config(u8 *data, u32 data_len, u32 codecid, GF_TextConfig *cfg) |
828 | 0 | { |
829 | 0 | u32 i; |
830 | 0 | Bool has_alt_format; |
831 | 0 | #ifndef GPAC_DISABLE_ISOM |
832 | 0 | Bool has_sd; |
833 | 0 | u32 j; |
834 | 0 | #endif |
835 | 0 | GF_Err e; |
836 | 0 | GF_BitStream *bs; |
837 | 0 | if (data || data_len || !cfg) return GF_BAD_PARAM; |
838 | 0 | if (codecid != GF_CODECID_TEXT_MPEG4) return GF_NOT_SUPPORTED; |
839 | | |
840 | | /*reset*/ |
841 | 0 | ResetTextConfig(cfg); |
842 | 0 | bs = gf_bs_new(data, data_len, GF_BITSTREAM_READ); |
843 | |
|
844 | 0 | e = GF_OK; |
845 | 0 | cfg->Base3GPPFormat = gf_bs_read_int(bs, 8); |
846 | 0 | cfg->MPEGExtendedFormat = gf_bs_read_int(bs, 8); |
847 | 0 | cfg->profileLevel = gf_bs_read_int(bs, 8); |
848 | 0 | cfg->timescale = gf_bs_read_int(bs, 24); |
849 | 0 | has_alt_format = (Bool)gf_bs_read_int(bs, 1); |
850 | 0 | cfg->sampleDescriptionFlags = gf_bs_read_int(bs, 2); |
851 | 0 | #ifndef GPAC_DISABLE_ISOM |
852 | 0 | has_sd = (Bool)gf_bs_read_int(bs, 1); |
853 | | #else |
854 | | gf_bs_read_int(bs, 1); |
855 | | #endif |
856 | 0 | cfg->has_vid_info = (Bool)gf_bs_read_int(bs, 1); |
857 | 0 | gf_bs_read_int(bs, 3); |
858 | 0 | cfg->layer = gf_bs_read_int(bs, 8); |
859 | 0 | cfg->text_width = gf_bs_read_int(bs, 16); |
860 | 0 | cfg->text_height = gf_bs_read_int(bs, 16); |
861 | 0 | if (has_alt_format) { |
862 | 0 | cfg->nb_compatible_formats = gf_bs_read_int(bs, 8); |
863 | 0 | for (i=0; i<cfg->nb_compatible_formats; i++) cfg->compatible_formats[i] = gf_bs_read_int(bs, 8); |
864 | 0 | } |
865 | 0 | #ifndef GPAC_DISABLE_ISOM |
866 | 0 | if (has_sd) { |
867 | 0 | u8 sample_index; |
868 | 0 | GF_TextSampleDescriptor *txdesc; |
869 | 0 | GF_Tx3gSampleEntryBox *a; |
870 | 0 | s64 avail; |
871 | 0 | u32 nb_desc = gf_bs_read_int(bs, 8); |
872 | | |
873 | | /*parse TTU[5]s*/ |
874 | 0 | avail = (s64) gf_bs_available(bs); |
875 | 0 | for (i=0; i<nb_desc; i++) { |
876 | 0 | sample_index = gf_bs_read_int(bs, 8); |
877 | 0 | avail -= 1; |
878 | 0 | e = gf_isom_box_parse((GF_Box **) &a, bs); |
879 | 0 | if (e) goto exit; |
880 | 0 | avail -= (s32) a->size; |
881 | |
|
882 | 0 | if (avail<0) { |
883 | 0 | e = GF_NON_COMPLIANT_BITSTREAM; |
884 | 0 | goto exit; |
885 | 0 | } |
886 | 0 | txdesc = (GF_TextSampleDescriptor *)gf_malloc(sizeof(GF_TextSampleDescriptor)); |
887 | 0 | txdesc->sample_index = sample_index; |
888 | 0 | txdesc->displayFlags = a->displayFlags; |
889 | 0 | txdesc->back_color = a->back_color; |
890 | 0 | txdesc->default_pos = a->default_box; |
891 | 0 | txdesc->default_style = a->default_style; |
892 | 0 | txdesc->vert_justif = a->vertical_justification; |
893 | 0 | txdesc->horiz_justif = a->horizontal_justification; |
894 | 0 | txdesc->font_count = a->font_table ? a->font_table->entry_count : 0; |
895 | 0 | if (txdesc->font_count) { |
896 | 0 | txdesc->fonts = (GF_FontRecord*)gf_malloc(sizeof(GF_FontRecord)*txdesc->font_count); |
897 | 0 | for (j=0; j<txdesc->font_count; j++) { |
898 | 0 | txdesc->fonts[j].fontID = a->font_table->fonts[j].fontID; |
899 | 0 | txdesc->fonts[j].fontName = a->font_table->fonts[j].fontName ? gf_strdup(a->font_table->fonts[j].fontName) : NULL; |
900 | 0 | } |
901 | 0 | } |
902 | 0 | gf_list_add(cfg->sample_descriptions, txdesc); |
903 | 0 | gf_isom_box_del((GF_Box *)a); |
904 | 0 | } |
905 | 0 | } |
906 | 0 | #endif |
907 | | |
908 | 0 | if (cfg->has_vid_info) { |
909 | 0 | cfg->video_width = gf_bs_read_int(bs, 16); |
910 | 0 | cfg->video_height = gf_bs_read_int(bs, 16); |
911 | 0 | cfg->horiz_offset = gf_bs_read_int(bs, 16); |
912 | 0 | cfg->vert_offset = gf_bs_read_int(bs, 16); |
913 | 0 | } |
914 | |
|
915 | 0 | #ifndef GPAC_DISABLE_ISOM |
916 | 0 | exit: |
917 | 0 | #endif |
918 | 0 | gf_bs_del(bs); |
919 | 0 | if (e) ResetTextConfig(cfg); |
920 | 0 | return e; |
921 | 0 | } |
922 | | |
923 | | |
924 | | |
925 | | GF_EXPORT |
926 | | GF_HEVCConfig *gf_odf_hevc_cfg_new() |
927 | 53.0k | { |
928 | 53.0k | GF_HEVCConfig *cfg; |
929 | 53.0k | GF_SAFEALLOC(cfg, GF_HEVCConfig); |
930 | 53.0k | if (!cfg) return NULL; |
931 | 53.0k | cfg->param_array = gf_list_new(); |
932 | 53.0k | cfg->nal_unit_size = 4; |
933 | 53.0k | return cfg; |
934 | 53.0k | } |
935 | | |
936 | | GF_EXPORT |
937 | | void gf_odf_hevc_cfg_del(GF_HEVCConfig *cfg) |
938 | 53.0k | { |
939 | 53.0k | if (!cfg) return; |
940 | 59.8k | while (gf_list_count(cfg->param_array)) { |
941 | 6.74k | GF_NALUFFParamArray *pa = (GF_NALUFFParamArray*)gf_list_get(cfg->param_array, 0); |
942 | 6.74k | gf_list_rem(cfg->param_array, 0); |
943 | | |
944 | 9.51k | while (gf_list_count(pa->nalus)) { |
945 | 2.76k | GF_NALUFFParam *n = (GF_NALUFFParam*)gf_list_get(pa->nalus, 0); |
946 | 2.76k | gf_list_rem(pa->nalus, 0); |
947 | 2.76k | if (n->data) gf_free(n->data); |
948 | 2.76k | gf_free(n); |
949 | 2.76k | } |
950 | 6.74k | gf_list_del(pa->nalus); |
951 | 6.74k | gf_free(pa); |
952 | 6.74k | } |
953 | 53.0k | gf_list_del(cfg->param_array); |
954 | 53.0k | gf_free(cfg); |
955 | 53.0k | } |
956 | | |
957 | | GF_EXPORT |
958 | | GF_Err gf_odf_hevc_cfg_write_bs(GF_HEVCConfig *cfg, GF_BitStream *bs) |
959 | 24.4k | { |
960 | 24.4k | u32 i, count; |
961 | | |
962 | 24.4k | count = gf_list_count(cfg->param_array); |
963 | | |
964 | 24.4k | if (!cfg->write_annex_b) { |
965 | 24.4k | gf_bs_write_int(bs, cfg->configurationVersion, 8); |
966 | | |
967 | 24.4k | if (!cfg->is_lhvc) { |
968 | 9.16k | gf_bs_write_int(bs, cfg->profile_space, 2); |
969 | 9.16k | gf_bs_write_int(bs, cfg->tier_flag, 1); |
970 | 9.16k | gf_bs_write_int(bs, cfg->profile_idc, 5); |
971 | 9.16k | gf_bs_write_int(bs, cfg->general_profile_compatibility_flags, 32); |
972 | 9.16k | gf_bs_write_int(bs, cfg->progressive_source_flag, 1); |
973 | 9.16k | gf_bs_write_int(bs, cfg->interlaced_source_flag, 1); |
974 | 9.16k | gf_bs_write_int(bs, cfg->non_packed_constraint_flag, 1); |
975 | 9.16k | gf_bs_write_int(bs, cfg->frame_only_constraint_flag, 1); |
976 | | /*only lowest 44 bits used*/ |
977 | 9.16k | gf_bs_write_long_int(bs, cfg->constraint_indicator_flags, 44); |
978 | 9.16k | gf_bs_write_int(bs, cfg->level_idc, 8); |
979 | 9.16k | } |
980 | | |
981 | 24.4k | gf_bs_write_int(bs, 0xFF, 4); |
982 | 24.4k | gf_bs_write_int(bs, cfg->min_spatial_segmentation_idc, 12); |
983 | | |
984 | 24.4k | gf_bs_write_int(bs, 0xFF, 6); |
985 | 24.4k | gf_bs_write_int(bs, cfg->parallelismType, 2); |
986 | | |
987 | 24.4k | if (!cfg->is_lhvc) { |
988 | 9.16k | gf_bs_write_int(bs, 0xFF, 6); |
989 | 9.16k | gf_bs_write_int(bs, cfg->chromaFormat, 2); |
990 | 9.16k | gf_bs_write_int(bs, 0xFF, 5); |
991 | 9.16k | gf_bs_write_int(bs, cfg->luma_bit_depth-8, 3); |
992 | 9.16k | gf_bs_write_int(bs, 0xFF, 5); |
993 | 9.16k | gf_bs_write_int(bs, cfg->chroma_bit_depth-8, 3); |
994 | 9.16k | gf_bs_write_int(bs, cfg->avgFrameRate, 16); |
995 | | |
996 | 9.16k | gf_bs_write_int(bs, cfg->constantFrameRate, 2); |
997 | 15.2k | } else { |
998 | 15.2k | gf_bs_write_int(bs, 0xFF, 2); |
999 | 15.2k | } |
1000 | | |
1001 | 24.4k | gf_bs_write_int(bs, cfg->numTemporalLayers, 3); |
1002 | 24.4k | gf_bs_write_int(bs, cfg->temporalIdNested, 1); |
1003 | 24.4k | gf_bs_write_int(bs, cfg->nal_unit_size - 1, 2); |
1004 | | |
1005 | 24.4k | gf_bs_write_int(bs, count, 8); |
1006 | 24.4k | } |
1007 | | |
1008 | 28.0k | for (i=0; i<count; i++) { |
1009 | 3.65k | u32 nalucount, j; |
1010 | 3.65k | GF_NALUFFParamArray *ar = (GF_NALUFFParamArray*)gf_list_get(cfg->param_array, i); |
1011 | | |
1012 | 3.65k | nalucount = gf_list_count(ar->nalus); |
1013 | 3.65k | if (!cfg->write_annex_b) { |
1014 | 3.65k | gf_bs_write_int(bs, ar->array_completeness, 1); |
1015 | 3.65k | gf_bs_write_int(bs, 0, 1); |
1016 | 3.65k | gf_bs_write_int(bs, ar->type, 6); |
1017 | 3.65k | gf_bs_write_int(bs, nalucount, 16); |
1018 | 3.65k | } |
1019 | | |
1020 | 5.12k | for (j=0; j<nalucount; j++) { |
1021 | 1.46k | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(ar->nalus, j); |
1022 | 1.46k | if (!cfg->write_annex_b) { |
1023 | 1.46k | gf_bs_write_int(bs, sl->size, 16); |
1024 | 1.46k | } else { |
1025 | 0 | gf_bs_write_u32(bs, 1); |
1026 | 0 | } |
1027 | 1.46k | gf_bs_write_data(bs, sl->data, sl->size); |
1028 | 1.46k | } |
1029 | 3.65k | } |
1030 | 24.4k | return GF_OK; |
1031 | 24.4k | } |
1032 | | |
1033 | | GF_EXPORT |
1034 | | GF_Err gf_odf_hevc_cfg_write(GF_HEVCConfig *cfg, u8 **outData, u32 *outSize) |
1035 | 23.9k | { |
1036 | 23.9k | GF_Err e; |
1037 | 23.9k | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
1038 | 23.9k | *outSize = 0; |
1039 | 23.9k | *outData = NULL; |
1040 | 23.9k | e = gf_odf_hevc_cfg_write_bs(cfg, bs); |
1041 | 23.9k | if (e==GF_OK) |
1042 | 23.9k | gf_bs_get_content(bs, outData, outSize); |
1043 | | |
1044 | 23.9k | gf_bs_del(bs); |
1045 | 23.9k | return e; |
1046 | 23.9k | } |
1047 | | |
1048 | | GF_EXPORT |
1049 | | GF_HEVCConfig *gf_odf_hevc_cfg_read_bs(GF_BitStream *bs, Bool is_lhvc) |
1050 | 6.58k | { |
1051 | 6.58k | u32 i, count; |
1052 | 6.58k | GF_HEVCConfig *cfg = gf_odf_hevc_cfg_new(); |
1053 | | |
1054 | 6.58k | cfg->is_lhvc = is_lhvc; |
1055 | | |
1056 | 6.58k | cfg->configurationVersion = gf_bs_read_int(bs, 8); |
1057 | | |
1058 | 6.58k | if (!is_lhvc) { |
1059 | 4.32k | cfg->profile_space = gf_bs_read_int(bs, 2); |
1060 | 4.32k | cfg->tier_flag = gf_bs_read_int(bs, 1); |
1061 | 4.32k | cfg->profile_idc = gf_bs_read_int(bs, 5); |
1062 | 4.32k | cfg->general_profile_compatibility_flags = gf_bs_read_int(bs, 32); |
1063 | | |
1064 | 4.32k | cfg->progressive_source_flag = gf_bs_read_int(bs, 1); |
1065 | 4.32k | cfg->interlaced_source_flag = gf_bs_read_int(bs, 1); |
1066 | 4.32k | cfg->non_packed_constraint_flag = gf_bs_read_int(bs, 1); |
1067 | 4.32k | cfg->frame_only_constraint_flag = gf_bs_read_int(bs, 1); |
1068 | | /*only lowest 44 bits used*/ |
1069 | 4.32k | cfg->constraint_indicator_flags = gf_bs_read_long_int(bs, 44); |
1070 | 4.32k | cfg->level_idc = gf_bs_read_int(bs, 8); |
1071 | 4.32k | } |
1072 | | |
1073 | 6.58k | gf_bs_read_int(bs, 4); //reserved |
1074 | 6.58k | cfg->min_spatial_segmentation_idc = gf_bs_read_int(bs, 12); |
1075 | | |
1076 | 6.58k | gf_bs_read_int(bs, 6);//reserved |
1077 | 6.58k | cfg->parallelismType = gf_bs_read_int(bs, 2); |
1078 | | |
1079 | 6.58k | if (!is_lhvc) { |
1080 | 4.32k | gf_bs_read_int(bs, 6); |
1081 | 4.32k | cfg->chromaFormat = gf_bs_read_int(bs, 2); |
1082 | 4.32k | gf_bs_read_int(bs, 5); |
1083 | 4.32k | cfg->luma_bit_depth = gf_bs_read_int(bs, 3) + 8; |
1084 | 4.32k | gf_bs_read_int(bs, 5); |
1085 | 4.32k | cfg->chroma_bit_depth = gf_bs_read_int(bs, 3) + 8; |
1086 | 4.32k | cfg->avgFrameRate = gf_bs_read_int(bs, 16); |
1087 | | |
1088 | 4.32k | cfg->constantFrameRate = gf_bs_read_int(bs, 2); |
1089 | 4.32k | } else { |
1090 | 2.26k | gf_bs_read_int(bs, 2); //reserved |
1091 | 2.26k | } |
1092 | | |
1093 | 6.58k | cfg->numTemporalLayers = gf_bs_read_int(bs, 3); |
1094 | 6.58k | cfg->temporalIdNested = gf_bs_read_int(bs, 1); |
1095 | | |
1096 | 6.58k | cfg->nal_unit_size = 1 + gf_bs_read_int(bs, 2); |
1097 | | |
1098 | 6.58k | count = gf_bs_read_int(bs, 8); |
1099 | 13.0k | for (i=0; i<count; i++) { |
1100 | 6.74k | u32 nalucount, j; |
1101 | 6.74k | GF_NALUFFParamArray *ar; |
1102 | 6.74k | GF_SAFEALLOC(ar, GF_NALUFFParamArray); |
1103 | 6.74k | if (!ar) { |
1104 | 0 | gf_odf_hevc_cfg_del(cfg); |
1105 | 0 | return NULL; |
1106 | 0 | } |
1107 | 6.74k | ar->nalus = gf_list_new(); |
1108 | 6.74k | gf_list_add(cfg->param_array, ar); |
1109 | | |
1110 | 6.74k | ar->array_completeness = gf_bs_read_int(bs, 1); |
1111 | 6.74k | gf_bs_read_int(bs, 1); |
1112 | 6.74k | ar->type = gf_bs_read_int(bs, 6); |
1113 | 6.74k | nalucount = gf_bs_read_int(bs, 16); |
1114 | 9.51k | for (j=0; j<nalucount; j++) { |
1115 | 3.07k | GF_NALUFFParam *sl; |
1116 | 3.07k | u32 size = gf_bs_read_int(bs, 16); |
1117 | 3.07k | if ((size>gf_bs_available(bs)) || (size<2)) { |
1118 | 309 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[HEVC] Wrong param set size %d\n", size)); |
1119 | 309 | gf_odf_hevc_cfg_del(cfg); |
1120 | 309 | return NULL; |
1121 | 309 | } |
1122 | 2.76k | GF_SAFEALLOC(sl, GF_NALUFFParam ); |
1123 | 2.76k | if (!sl) { |
1124 | 0 | gf_odf_hevc_cfg_del(cfg); |
1125 | 0 | return NULL; |
1126 | 0 | } |
1127 | | |
1128 | 2.76k | sl->size = size; |
1129 | 2.76k | sl->data = (char *)gf_malloc(sizeof(char) * sl->size); |
1130 | 2.76k | gf_bs_read_data(bs, sl->data, sl->size); |
1131 | 2.76k | gf_list_add(ar->nalus, sl); |
1132 | 2.76k | } |
1133 | 6.74k | } |
1134 | 6.27k | return cfg; |
1135 | 6.58k | } |
1136 | | |
1137 | | GF_EXPORT |
1138 | | GF_HEVCConfig *gf_odf_hevc_cfg_read(u8 *dsi, u32 dsi_size, Bool is_lhvc) |
1139 | 4.94k | { |
1140 | 4.94k | GF_BitStream *bs = gf_bs_new(dsi, dsi_size, GF_BITSTREAM_READ); |
1141 | 4.94k | GF_HEVCConfig *cfg = gf_odf_hevc_cfg_read_bs(bs, is_lhvc); |
1142 | 4.94k | gf_bs_del(bs); |
1143 | 4.94k | return cfg; |
1144 | 4.94k | } |
1145 | | |
1146 | | GF_EXPORT |
1147 | | GF_VVCConfig *gf_odf_vvc_cfg_new() |
1148 | 71.3k | { |
1149 | 71.3k | GF_VVCConfig *cfg; |
1150 | 71.3k | GF_SAFEALLOC(cfg, GF_VVCConfig); |
1151 | 71.3k | if (!cfg) return NULL; |
1152 | 71.3k | cfg->param_array = gf_list_new(); |
1153 | 71.3k | cfg->nal_unit_size = 4; |
1154 | 71.3k | cfg->chroma_format = 1; |
1155 | 71.3k | cfg->bit_depth = 8; |
1156 | 71.3k | return cfg; |
1157 | 71.3k | } |
1158 | | |
1159 | | GF_EXPORT |
1160 | | void gf_odf_vvc_cfg_del(GF_VVCConfig *cfg) |
1161 | 71.3k | { |
1162 | 71.3k | if (!cfg) return; |
1163 | 72.9k | while (gf_list_count(cfg->param_array)) { |
1164 | 1.67k | GF_NALUFFParamArray *pa = (GF_NALUFFParamArray*)gf_list_get(cfg->param_array, 0); |
1165 | 1.67k | gf_list_rem(cfg->param_array, 0); |
1166 | | |
1167 | 2.32k | while (gf_list_count(pa->nalus)) { |
1168 | 654 | GF_NALUFFParam *n = (GF_NALUFFParam*)gf_list_get(pa->nalus, 0); |
1169 | 654 | gf_list_rem(pa->nalus, 0); |
1170 | 654 | if (n->data) gf_free(n->data); |
1171 | 654 | gf_free(n); |
1172 | 654 | } |
1173 | 1.67k | gf_list_del(pa->nalus); |
1174 | 1.67k | gf_free(pa); |
1175 | 1.67k | } |
1176 | 71.3k | gf_list_del(cfg->param_array); |
1177 | 71.3k | if (cfg->general_constraint_info) |
1178 | 39.3k | gf_free(cfg->general_constraint_info); |
1179 | 71.3k | if (cfg->sub_profiles_idc) |
1180 | 533 | gf_free(cfg->sub_profiles_idc); |
1181 | 71.3k | gf_free(cfg); |
1182 | 71.3k | } |
1183 | | |
1184 | | GF_EXPORT |
1185 | | GF_Err gf_odf_vvc_cfg_write_bs(GF_VVCConfig *cfg, GF_BitStream *bs) |
1186 | 43.6k | { |
1187 | 43.6k | u32 i, count; |
1188 | | |
1189 | 43.6k | count = gf_list_count(cfg->param_array); |
1190 | | |
1191 | 43.6k | if (!cfg->write_annex_b) { |
1192 | | |
1193 | 43.6k | gf_bs_write_int(bs, 0xFF, 5); |
1194 | 43.6k | gf_bs_write_int(bs, cfg->nal_unit_size - 1, 2); |
1195 | 43.6k | gf_bs_write_int(bs, cfg->ptl_present, 1); |
1196 | | |
1197 | 43.6k | if (cfg->ptl_present) { |
1198 | 22.9k | s32 idx; |
1199 | | |
1200 | 22.9k | gf_bs_write_int(bs, cfg->ols_idx, 9); |
1201 | 22.9k | gf_bs_write_int(bs, cfg->numTemporalLayers, 3); |
1202 | 22.9k | gf_bs_write_int(bs, cfg->constantFrameRate, 2); |
1203 | 22.9k | gf_bs_write_int(bs, cfg->chroma_format, 2); |
1204 | 22.9k | gf_bs_write_int(bs, cfg->bit_depth - 8, 3); |
1205 | 22.9k | gf_bs_write_int(bs, 0xFF, 5); |
1206 | | |
1207 | 22.9k | if (!cfg->general_constraint_info) |
1208 | 0 | cfg->num_constraint_info = 0; |
1209 | | |
1210 | | //write PTL |
1211 | 22.9k | gf_bs_write_int(bs, 0, 2); |
1212 | 22.9k | gf_bs_write_int(bs, cfg->num_constraint_info, 6); |
1213 | 22.9k | gf_bs_write_int(bs, cfg->general_profile_idc, 7); |
1214 | 22.9k | gf_bs_write_int(bs, cfg->general_tier_flag, 1); |
1215 | 22.9k | gf_bs_write_u8(bs, cfg->general_level_idc); |
1216 | 22.9k | gf_bs_write_int(bs, cfg->ptl_frame_only_constraint, 1); |
1217 | 22.9k | gf_bs_write_int(bs, cfg->ptl_multilayer_enabled, 1); |
1218 | | |
1219 | 22.9k | if (cfg->num_constraint_info) { |
1220 | 22.9k | gf_bs_write_data(bs, cfg->general_constraint_info, cfg->num_constraint_info - 1); |
1221 | 22.9k | gf_bs_write_int(bs, cfg->general_constraint_info[cfg->num_constraint_info - 1], 6); |
1222 | 22.9k | } else { |
1223 | 0 | gf_bs_write_int(bs, 0, 6); |
1224 | 0 | } |
1225 | | |
1226 | 35.6k | for (idx=cfg->numTemporalLayers-2; idx>=0; idx--) { |
1227 | 12.6k | u8 val = cfg->ptl_sublayer_present_mask & (1<<idx); |
1228 | 12.6k | gf_bs_write_int(bs, val ? 1 : 0, 1); |
1229 | 12.6k | } |
1230 | 47.1k | for (idx=cfg->numTemporalLayers; idx<=8 && cfg->numTemporalLayers>1; idx++) { |
1231 | 24.2k | gf_bs_write_int(bs, 0, 1); |
1232 | 24.2k | } |
1233 | 35.6k | for (idx=cfg->numTemporalLayers-2; idx>=0; idx--) { |
1234 | 12.6k | if (cfg->ptl_sublayer_present_mask & (1<<idx)) |
1235 | 0 | gf_bs_write_u8(bs, cfg->sublayer_level_idc[idx]); |
1236 | 12.6k | } |
1237 | 22.9k | if (!cfg->sub_profiles_idc) cfg->num_sub_profiles = 0; |
1238 | 22.9k | gf_bs_write_u8(bs, cfg->num_sub_profiles); |
1239 | 22.9k | for (idx=0; idx<cfg->num_sub_profiles; idx++) { |
1240 | 0 | gf_bs_write_u32(bs, cfg->sub_profiles_idc[idx]); |
1241 | 0 | } |
1242 | | //end PTL |
1243 | | |
1244 | 22.9k | gf_bs_write_u16(bs, cfg->maxPictureWidth); |
1245 | 22.9k | gf_bs_write_u16(bs, cfg->maxPictureHeight); |
1246 | 22.9k | gf_bs_write_u16(bs, cfg->avgFrameRate); |
1247 | 22.9k | } |
1248 | 43.6k | gf_bs_write_int(bs, count, 8); |
1249 | 43.6k | } |
1250 | | |
1251 | 43.6k | for (i=0; i<count; i++) { |
1252 | 0 | u32 nalucount, j; |
1253 | 0 | GF_NALUFFParamArray *ar = (GF_NALUFFParamArray*)gf_list_get(cfg->param_array, i); |
1254 | |
|
1255 | 0 | nalucount = gf_list_count(ar->nalus); |
1256 | 0 | if (!cfg->write_annex_b) { |
1257 | 0 | gf_bs_write_int(bs, ar->array_completeness, 1); |
1258 | 0 | gf_bs_write_int(bs, 0, 2); |
1259 | 0 | gf_bs_write_int(bs, ar->type, 5); |
1260 | |
|
1261 | 0 | if ((ar->type != GF_VVC_NALU_DEC_PARAM) && (ar->type != GF_VVC_NALU_OPI)) |
1262 | 0 | gf_bs_write_int(bs, nalucount, 16); |
1263 | 0 | else |
1264 | 0 | nalucount = 1; |
1265 | 0 | } |
1266 | |
|
1267 | 0 | for (j=0; j<nalucount; j++) { |
1268 | 0 | GF_NALUFFParam *sl = (GF_NALUFFParam *)gf_list_get(ar->nalus, j); |
1269 | 0 | if (!cfg->write_annex_b) { |
1270 | 0 | gf_bs_write_int(bs, sl->size, 16); |
1271 | 0 | } else { |
1272 | 0 | gf_bs_write_u32(bs, 1); |
1273 | 0 | } |
1274 | 0 | gf_bs_write_data(bs, sl->data, sl->size); |
1275 | 0 | } |
1276 | 0 | } |
1277 | 43.6k | return GF_OK; |
1278 | 43.6k | } |
1279 | | |
1280 | | GF_EXPORT |
1281 | | GF_Err gf_odf_vvc_cfg_write(GF_VVCConfig *cfg, u8 **outData, u32 *outSize) |
1282 | 43.6k | { |
1283 | 43.6k | GF_Err e; |
1284 | 43.6k | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
1285 | 43.6k | *outSize = 0; |
1286 | 43.6k | *outData = NULL; |
1287 | 43.6k | e = gf_odf_vvc_cfg_write_bs(cfg, bs); |
1288 | 43.6k | if (e==GF_OK) |
1289 | 43.6k | gf_bs_get_content(bs, outData, outSize); |
1290 | | |
1291 | 43.6k | gf_bs_del(bs); |
1292 | 43.6k | return e; |
1293 | 43.6k | } |
1294 | | |
1295 | | GF_EXPORT |
1296 | | GF_VVCConfig *gf_odf_vvc_cfg_read_bs(GF_BitStream *bs) |
1297 | 27.6k | { |
1298 | 27.6k | u32 i, count; |
1299 | 27.6k | GF_VVCConfig *cfg = gf_odf_vvc_cfg_new(); |
1300 | | |
1301 | 27.6k | gf_bs_read_int(bs, 5); |
1302 | 27.6k | cfg->nal_unit_size = 1 + gf_bs_read_int(bs, 2); |
1303 | 27.6k | cfg->ptl_present = gf_bs_read_int(bs, 1); |
1304 | | |
1305 | 27.6k | if (cfg->ptl_present) { |
1306 | 16.6k | s32 j; |
1307 | | |
1308 | 16.6k | cfg->ols_idx = gf_bs_read_int(bs, 9); |
1309 | 16.6k | cfg->numTemporalLayers = gf_bs_read_int(bs, 3); |
1310 | 16.6k | cfg->constantFrameRate = gf_bs_read_int(bs, 2); |
1311 | 16.6k | cfg->chroma_format = gf_bs_read_int(bs, 2); |
1312 | 16.6k | cfg->bit_depth = 8 + gf_bs_read_int(bs, 3); |
1313 | 16.6k | gf_bs_read_int(bs, 5); |
1314 | | |
1315 | | //parse PTL |
1316 | 16.6k | gf_bs_read_int(bs, 2); |
1317 | 16.6k | cfg->num_constraint_info = gf_bs_read_int(bs, 6); |
1318 | 16.6k | cfg->general_profile_idc = gf_bs_read_int(bs, 7); |
1319 | 16.6k | cfg->general_tier_flag = gf_bs_read_int(bs, 1); |
1320 | 16.6k | cfg->general_level_idc = gf_bs_read_u8(bs); |
1321 | 16.6k | cfg->ptl_frame_only_constraint = gf_bs_read_int(bs, 1); |
1322 | 16.6k | cfg->ptl_multilayer_enabled = gf_bs_read_int(bs, 1); |
1323 | | |
1324 | 16.6k | if (cfg->num_constraint_info) { |
1325 | 16.3k | cfg->general_constraint_info = gf_malloc(sizeof(u8)*cfg->num_constraint_info); |
1326 | 16.3k | if (!cfg->general_constraint_info) { |
1327 | 0 | gf_free(cfg); |
1328 | 0 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VVC] alloc failed while parsing vvc config\n")); |
1329 | 0 | return NULL; |
1330 | 0 | } |
1331 | 16.3k | gf_bs_read_data(bs, cfg->general_constraint_info, cfg->num_constraint_info - 1); |
1332 | 16.3k | cfg->general_constraint_info[cfg->num_constraint_info-1] = gf_bs_read_int(bs, 6); |
1333 | 16.3k | } else { |
1334 | | //forbidden in spec! |
1335 | 299 | gf_bs_read_int(bs, 6); |
1336 | 299 | } |
1337 | | |
1338 | 16.6k | cfg->ptl_sublayer_present_mask = 0; |
1339 | 24.3k | for (j=cfg->numTemporalLayers-2; j>=0; j--) { |
1340 | 7.71k | u32 val = gf_bs_read_int(bs, 1); |
1341 | 7.71k | cfg->ptl_sublayer_present_mask |= val << j; |
1342 | 7.71k | } |
1343 | 33.3k | for (j=cfg->numTemporalLayers; j<=8 && cfg->numTemporalLayers>1; j++) { |
1344 | 16.7k | gf_bs_read_int(bs, 1); |
1345 | 16.7k | } |
1346 | 24.3k | for (j=cfg->numTemporalLayers-2; j>=0; j--) { |
1347 | 7.71k | if (cfg->ptl_sublayer_present_mask & (1<<j)) { |
1348 | 1.70k | cfg->sublayer_level_idc[j] = gf_bs_read_u8(bs); |
1349 | 1.70k | } |
1350 | 7.71k | } |
1351 | 16.6k | cfg->num_sub_profiles = gf_bs_read_u8(bs); |
1352 | 16.6k | if (cfg->num_sub_profiles) { |
1353 | 533 | cfg->sub_profiles_idc = gf_malloc(sizeof(u32)*cfg->num_sub_profiles); |
1354 | 533 | if (!cfg->sub_profiles_idc) { |
1355 | 0 | gf_free(cfg->general_constraint_info); |
1356 | 0 | gf_free(cfg); |
1357 | 0 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VVC] alloc failed while parsing vvc config\n")); |
1358 | 0 | return NULL; |
1359 | 0 | } |
1360 | 533 | } |
1361 | 76.8k | for (i=0; i<cfg->num_sub_profiles; i++) { |
1362 | 60.2k | cfg->sub_profiles_idc[i] = gf_bs_read_u32(bs); |
1363 | 60.2k | } |
1364 | | |
1365 | | //end PTL |
1366 | | |
1367 | 16.6k | cfg->maxPictureWidth = gf_bs_read_u16(bs); |
1368 | 16.6k | cfg->maxPictureHeight = gf_bs_read_u16(bs); |
1369 | 16.6k | cfg->avgFrameRate = gf_bs_read_u16(bs); |
1370 | 16.6k | } |
1371 | | |
1372 | 27.6k | count = gf_bs_read_int(bs, 8); |
1373 | 33.4k | for (i=0; i<count; i++) { |
1374 | 7.76k | u32 nalucount, j; |
1375 | 7.76k | Bool valid = GF_FALSE; |
1376 | 7.76k | GF_NALUFFParamArray *ar; |
1377 | 7.76k | GF_SAFEALLOC(ar, GF_NALUFFParamArray); |
1378 | 7.76k | if (!ar) { |
1379 | 0 | gf_odf_vvc_cfg_del(cfg); |
1380 | 0 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VVC] alloc failed while parsing vvc config\n")); |
1381 | 0 | return NULL; |
1382 | 0 | } |
1383 | 7.76k | ar->array_completeness = gf_bs_read_int(bs, 1); |
1384 | 7.76k | gf_bs_read_int(bs, 2); |
1385 | 7.76k | ar->type = gf_bs_read_int(bs, 5); |
1386 | | |
1387 | 7.76k | switch (ar->type) { |
1388 | 378 | case GF_VVC_NALU_DEC_PARAM: |
1389 | 520 | case GF_VVC_NALU_OPI: |
1390 | 625 | case GF_VVC_NALU_VID_PARAM: |
1391 | 711 | case GF_VVC_NALU_SEQ_PARAM: |
1392 | 974 | case GF_VVC_NALU_PIC_PARAM: |
1393 | 1.29k | case GF_VVC_NALU_SEI_PREFIX: |
1394 | 1.67k | case GF_VVC_NALU_SEI_SUFFIX: |
1395 | 1.67k | valid = GF_TRUE; |
1396 | 1.67k | ar->nalus = gf_list_new(); |
1397 | 1.67k | gf_list_add(cfg->param_array, ar); |
1398 | 1.67k | break; |
1399 | 6.09k | default: |
1400 | 6.09k | GF_LOG(GF_LOG_WARNING, GF_LOG_CODING, ("[VVC] Invalid NALU type %d in vvcC - ignoring\n", ar->type)); |
1401 | 6.09k | gf_free(ar); |
1402 | 6.09k | break; |
1403 | 7.76k | } |
1404 | | |
1405 | 7.76k | if (!valid || ((ar->type != GF_VVC_NALU_DEC_PARAM) && (ar->type != GF_VVC_NALU_OPI))) |
1406 | 7.24k | nalucount = gf_bs_read_int(bs, 16); |
1407 | 520 | else |
1408 | 520 | nalucount = 1; |
1409 | | |
1410 | 8.87k | for (j=0; j<nalucount; j++) { |
1411 | 3.04k | GF_NALUFFParam *sl; |
1412 | 3.04k | u32 size = gf_bs_read_int(bs, 16); |
1413 | 3.04k | if ((size>gf_bs_available(bs)) || (size<2)) { |
1414 | 1.93k | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VVC] Wrong param set size %d\n", size)); |
1415 | 1.93k | gf_odf_vvc_cfg_del(cfg); |
1416 | 1.93k | return NULL; |
1417 | 1.93k | } |
1418 | 1.11k | if (!valid) { |
1419 | 458 | gf_bs_skip_bytes(bs, size); |
1420 | 458 | continue; |
1421 | 458 | } |
1422 | 654 | GF_SAFEALLOC(sl, GF_NALUFFParam ); |
1423 | 654 | if (!sl) { |
1424 | 0 | gf_odf_vvc_cfg_del(cfg); |
1425 | 0 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VVC] alloc failed while parsing vvc config\n")); |
1426 | 0 | return NULL; |
1427 | 0 | } |
1428 | | |
1429 | 654 | sl->size = size; |
1430 | 654 | sl->data = (char *)gf_malloc(sizeof(char) * sl->size); |
1431 | 654 | if (!sl->data) { |
1432 | 0 | gf_free(sl); |
1433 | 0 | gf_odf_vvc_cfg_del(cfg); |
1434 | 0 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VVC] alloc failed while parsing vvc config\n")); |
1435 | 0 | return NULL; |
1436 | 0 | } |
1437 | 654 | gf_bs_read_data(bs, sl->data, sl->size); |
1438 | 654 | gf_list_add(ar->nalus, sl); |
1439 | 654 | } |
1440 | 7.76k | } |
1441 | 25.7k | return cfg; |
1442 | 27.6k | } |
1443 | | |
1444 | | GF_EXPORT |
1445 | | GF_VVCConfig *gf_odf_vvc_cfg_read(u8 *dsi, u32 dsi_size) |
1446 | 24.6k | { |
1447 | 24.6k | GF_BitStream *bs = gf_bs_new(dsi, dsi_size, GF_BITSTREAM_READ); |
1448 | 24.6k | GF_VVCConfig *cfg = gf_odf_vvc_cfg_read_bs(bs); |
1449 | 24.6k | gf_bs_del(bs); |
1450 | 24.6k | return cfg; |
1451 | 24.6k | } |
1452 | | |
1453 | | GF_EXPORT |
1454 | | GF_AV1Config *gf_odf_av1_cfg_new() |
1455 | 50.3k | { |
1456 | 50.3k | GF_AV1Config *cfg; |
1457 | 50.3k | GF_SAFEALLOC(cfg, GF_AV1Config); |
1458 | 50.3k | if (!cfg) return NULL; |
1459 | 50.3k | cfg->marker = 1; |
1460 | 50.3k | cfg->version = 1; |
1461 | 50.3k | cfg->initial_presentation_delay_minus_one = 0; |
1462 | 50.3k | cfg->obu_array = gf_list_new(); |
1463 | 50.3k | return cfg; |
1464 | 50.3k | } |
1465 | | |
1466 | | GF_EXPORT |
1467 | | void gf_odf_av1_cfg_del(GF_AV1Config *cfg) |
1468 | 50.7k | { |
1469 | 50.7k | if (!cfg) return; |
1470 | 371k | while (gf_list_count(cfg->obu_array)) { |
1471 | 320k | GF_AV1_OBUArrayEntry *a = (GF_AV1_OBUArrayEntry*)gf_list_get(cfg->obu_array, 0); |
1472 | 320k | if (a->obu) gf_free(a->obu); |
1473 | 320k | gf_list_rem(cfg->obu_array, 0); |
1474 | 320k | gf_free(a); |
1475 | 320k | } |
1476 | 50.7k | gf_list_del(cfg->obu_array); |
1477 | 50.7k | gf_free(cfg); |
1478 | 50.7k | } |
1479 | | |
1480 | | GF_EXPORT |
1481 | | GF_Err gf_odf_av1_cfg_write_bs(GF_AV1Config *cfg, GF_BitStream *bs) |
1482 | 11.0k | { |
1483 | 11.0k | u32 i = 0; |
1484 | 11.0k | gf_bs_write_int(bs, cfg->marker, 1); |
1485 | 11.0k | gf_assert(cfg->marker == 1); |
1486 | 11.0k | gf_bs_write_int(bs, cfg->version, 7); |
1487 | 11.0k | gf_assert(cfg->version == 1); |
1488 | 11.0k | gf_bs_write_int(bs, cfg->seq_profile, 3); |
1489 | 11.0k | gf_bs_write_int(bs, cfg->seq_level_idx_0, 5); |
1490 | 11.0k | gf_bs_write_int(bs, cfg->seq_tier_0, 1); |
1491 | 11.0k | gf_bs_write_int(bs, cfg->high_bitdepth, 1); |
1492 | 11.0k | gf_bs_write_int(bs, cfg->twelve_bit, 1); |
1493 | 11.0k | gf_bs_write_int(bs, cfg->monochrome, 1); |
1494 | 11.0k | gf_bs_write_int(bs, cfg->chroma_subsampling_x, 1); |
1495 | 11.0k | gf_bs_write_int(bs, cfg->chroma_subsampling_y, 1); |
1496 | 11.0k | gf_bs_write_int(bs, cfg->chroma_sample_position, 2); |
1497 | 11.0k | gf_bs_write_int(bs, 0, 3); /*reserved*/ |
1498 | 11.0k | gf_bs_write_int(bs, cfg->initial_presentation_delay_present, 1); |
1499 | 11.0k | gf_bs_write_int(bs, cfg->initial_presentation_delay_minus_one, 4); /*TODO: compute initial_presentation_delay_minus_one*/ |
1500 | 270k | for (i = 0; i < gf_list_count(cfg->obu_array); ++i) { |
1501 | 259k | GF_AV1_OBUArrayEntry *a = gf_list_get(cfg->obu_array, i); |
1502 | 259k | gf_bs_write_data(bs, a->obu, (u32)a->obu_length); //TODO: we are supposed to omit the size on the last OBU... |
1503 | 259k | } |
1504 | 11.0k | return GF_OK; |
1505 | 11.0k | } |
1506 | | |
1507 | | GF_EXPORT |
1508 | 11.0k | GF_Err gf_odf_av1_cfg_write(GF_AV1Config *cfg, u8 **outData, u32 *outSize) { |
1509 | 11.0k | GF_Err e; |
1510 | 11.0k | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
1511 | 11.0k | *outSize = 0; |
1512 | 11.0k | *outData = NULL; |
1513 | 11.0k | e = gf_odf_av1_cfg_write_bs(cfg, bs); |
1514 | 11.0k | if (e == GF_OK) |
1515 | 11.0k | gf_bs_get_content(bs, outData, outSize); |
1516 | | |
1517 | 11.0k | gf_bs_del(bs); |
1518 | 11.0k | return e; |
1519 | 11.0k | } |
1520 | | |
1521 | | GF_EXPORT |
1522 | | GF_VPConfig *gf_odf_vp_cfg_new() |
1523 | 1.81k | { |
1524 | 1.81k | GF_VPConfig *cfg; |
1525 | 1.81k | GF_SAFEALLOC(cfg, GF_VPConfig); |
1526 | 1.81k | if (!cfg) return NULL; |
1527 | 1.81k | cfg->codec_initdata_size = 0; |
1528 | 1.81k | cfg->codec_initdata = NULL; |
1529 | 1.81k | return cfg; |
1530 | 1.81k | } |
1531 | | |
1532 | | GF_EXPORT |
1533 | | void gf_odf_vp_cfg_del(GF_VPConfig *cfg) |
1534 | 1.81k | { |
1535 | 1.81k | if (!cfg) return; |
1536 | | |
1537 | 1.81k | if (cfg->codec_initdata) { |
1538 | 0 | gf_free(cfg->codec_initdata); |
1539 | 0 | cfg->codec_initdata = NULL; |
1540 | 0 | } |
1541 | | |
1542 | 1.81k | gf_free(cfg); |
1543 | 1.81k | } |
1544 | | |
1545 | | GF_EXPORT |
1546 | | GF_Err gf_odf_vp_cfg_write_bs(GF_VPConfig *cfg, GF_BitStream *bs, Bool is_v0) |
1547 | 601 | { |
1548 | 601 | gf_bs_write_int(bs, cfg->profile, 8); |
1549 | 601 | gf_bs_write_int(bs, cfg->level, 8); |
1550 | 601 | gf_bs_write_int(bs, cfg->bit_depth, 4); |
1551 | 601 | gf_bs_write_int(bs, cfg->chroma_subsampling, 3); |
1552 | 601 | gf_bs_write_int(bs, cfg->video_fullRange_flag, 1); |
1553 | 601 | gf_bs_write_int(bs, cfg->colour_primaries, 8); |
1554 | 601 | gf_bs_write_int(bs, cfg->transfer_characteristics, 8); |
1555 | 601 | gf_bs_write_int(bs, cfg->matrix_coefficients, 8); |
1556 | | |
1557 | 601 | if (!is_v0) { |
1558 | 601 | if (cfg->codec_initdata_size) { |
1559 | 0 | GF_LOG(GF_LOG_WARNING, GF_LOG_CODING, ("[VPX] Invalid data in configuration: codec_initdata_size must be 0, was %d - ignoring\n", cfg->codec_initdata_size)); |
1560 | 0 | } |
1561 | | |
1562 | 601 | gf_bs_write_int(bs, (u16)0, 16); |
1563 | 601 | } |
1564 | | |
1565 | 601 | return GF_OK; |
1566 | 601 | } |
1567 | | |
1568 | | GF_EXPORT |
1569 | | GF_Err gf_odf_vp_cfg_write(GF_VPConfig *cfg, u8 **outData, u32 *outSize, Bool is_v0) |
1570 | 601 | { |
1571 | 601 | GF_Err e; |
1572 | 601 | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
1573 | 601 | *outSize = 0; |
1574 | 601 | *outData = NULL; |
1575 | 601 | e = gf_odf_vp_cfg_write_bs(cfg, bs, is_v0); |
1576 | 601 | if (e==GF_OK) |
1577 | 601 | gf_bs_get_content(bs, outData, outSize); |
1578 | | |
1579 | 601 | gf_bs_del(bs); |
1580 | 601 | return e; |
1581 | 601 | } |
1582 | | |
1583 | | GF_EXPORT |
1584 | | GF_VPConfig *gf_odf_vp_cfg_read_bs(GF_BitStream *bs, Bool is_v0) |
1585 | 1.32k | { |
1586 | 1.32k | GF_VPConfig *cfg = gf_odf_vp_cfg_new(); |
1587 | | |
1588 | 1.32k | cfg->profile = gf_bs_read_int(bs, 8); |
1589 | 1.32k | cfg->level = gf_bs_read_int(bs, 8); |
1590 | | |
1591 | 1.32k | cfg->bit_depth = gf_bs_read_int(bs, 4); |
1592 | 1.32k | cfg->chroma_subsampling = gf_bs_read_int(bs, 3); |
1593 | 1.32k | cfg->video_fullRange_flag = gf_bs_read_int(bs, 1); |
1594 | | |
1595 | 1.32k | cfg->colour_primaries = gf_bs_read_int(bs, 8); |
1596 | 1.32k | cfg->transfer_characteristics = gf_bs_read_int(bs, 8); |
1597 | 1.32k | cfg->matrix_coefficients = gf_bs_read_int(bs, 8); |
1598 | | |
1599 | 1.32k | if (is_v0) |
1600 | 633 | return cfg; |
1601 | | |
1602 | 693 | cfg->codec_initdata_size = gf_bs_read_int(bs, 16); |
1603 | | |
1604 | | // must be 0 according to spec |
1605 | 693 | if (cfg->codec_initdata_size) { |
1606 | 167 | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[VPX] Invalid data in configuration: codec_initdata_size must be 0, was %d\n", cfg->codec_initdata_size)); |
1607 | 167 | gf_odf_vp_cfg_del(cfg); |
1608 | 167 | return NULL; |
1609 | 167 | } |
1610 | | |
1611 | 526 | return cfg; |
1612 | 693 | } |
1613 | | |
1614 | | GF_EXPORT |
1615 | | GF_VPConfig *gf_odf_vp_cfg_read(u8 *dsi, u32 dsi_size) |
1616 | 42 | { |
1617 | 42 | GF_BitStream *bs = gf_bs_new(dsi, dsi_size, GF_BITSTREAM_READ); |
1618 | 42 | GF_VPConfig *cfg = gf_odf_vp_cfg_read_bs(bs, GF_FALSE); |
1619 | 42 | gf_bs_del(bs); |
1620 | 42 | return cfg; |
1621 | 42 | } |
1622 | | |
1623 | | GF_EXPORT |
1624 | | GF_AV1Config *gf_odf_av1_cfg_read_bs_size(GF_BitStream *bs, u32 size) |
1625 | 46.4k | { |
1626 | 46.4k | #ifndef GPAC_DISABLE_AV_PARSERS |
1627 | 46.4k | AV1State state; |
1628 | 46.4k | u8 reserved; |
1629 | 46.4k | GF_AV1Config *cfg; |
1630 | | |
1631 | 46.4k | if (!size) size = (u32) gf_bs_available(bs); |
1632 | 46.4k | if (!size) return NULL; |
1633 | | |
1634 | 46.3k | cfg = gf_odf_av1_cfg_new(); |
1635 | 46.3k | gf_av1_init_state(&state); |
1636 | 46.3k | state.config = cfg; |
1637 | | |
1638 | 46.3k | cfg->marker = gf_bs_read_int(bs, 1); |
1639 | 46.3k | cfg->version = gf_bs_read_int(bs, 7); |
1640 | 46.3k | cfg->seq_profile = gf_bs_read_int(bs, 3); |
1641 | 46.3k | cfg->seq_level_idx_0 = gf_bs_read_int(bs, 5); |
1642 | 46.3k | cfg->seq_tier_0 = gf_bs_read_int(bs, 1); |
1643 | 46.3k | cfg->high_bitdepth = gf_bs_read_int(bs, 1); |
1644 | 46.3k | cfg->twelve_bit = gf_bs_read_int(bs, 1); |
1645 | 46.3k | cfg->monochrome = gf_bs_read_int(bs, 1); |
1646 | 46.3k | cfg->chroma_subsampling_x = gf_bs_read_int(bs, 1); |
1647 | 46.3k | cfg->chroma_subsampling_y = gf_bs_read_int(bs, 1); |
1648 | 46.3k | cfg->chroma_sample_position = gf_bs_read_int(bs, 2); |
1649 | | |
1650 | 46.3k | reserved = gf_bs_read_int(bs, 3); |
1651 | 46.3k | cfg->initial_presentation_delay_present = gf_bs_read_int(bs, 1); |
1652 | 46.3k | if (cfg->initial_presentation_delay_present) { |
1653 | 19.6k | cfg->initial_presentation_delay_minus_one = gf_bs_read_int(bs, 4); |
1654 | 26.7k | } else { |
1655 | 26.7k | /*reserved = */gf_bs_read_int(bs, 4); |
1656 | 26.7k | cfg->initial_presentation_delay_minus_one = 0; |
1657 | 26.7k | } |
1658 | 46.3k | size -= 4; |
1659 | | |
1660 | 46.3k | if (reserved != 0 || cfg->marker != 1 || cfg->version != 1) { |
1661 | 2.91k | GF_LOG(GF_LOG_DEBUG, GF_LOG_CODING, ("[AV1] wrong av1C reserved %d / marker %d / version %d expecting 0 1 1\n", reserved, cfg->marker, cfg->version)); |
1662 | 2.91k | gf_odf_av1_cfg_del(cfg); |
1663 | 2.91k | return NULL; |
1664 | 2.91k | } |
1665 | | |
1666 | | |
1667 | 310k | while (size) { |
1668 | 298k | u64 pos, obu_size; |
1669 | 298k | ObuType obu_type; |
1670 | 298k | GF_AV1_OBUArrayEntry *a; |
1671 | | |
1672 | 298k | pos = gf_bs_get_position(bs); |
1673 | 298k | obu_size = 0; |
1674 | 298k | if (gf_av1_parse_obu(bs, &obu_type, &obu_size, NULL, &state) != GF_OK) { |
1675 | 29.9k | GF_LOG(GF_LOG_ERROR, GF_LOG_CODING, ("[AV1] could not parse AV1 OBU at position "LLU". Leaving parsing.\n", pos)); |
1676 | 29.9k | break; |
1677 | 29.9k | } |
1678 | 268k | gf_assert(obu_size == gf_bs_get_position(bs) - pos); |
1679 | 268k | GF_LOG(GF_LOG_DEBUG, GF_LOG_CODING, ("[AV1] parsed AV1 OBU type=%u size="LLU" at position "LLU".\n", obu_type, obu_size, pos)); |
1680 | | |
1681 | 268k | if (!av1_is_obu_header(obu_type)) { |
1682 | 110k | GF_LOG(GF_LOG_DEBUG, GF_LOG_CODING, ("[AV1] AV1 unexpected OBU type=%u size="LLU" found at position "LLU". Forwarding.\n", pos)); |
1683 | 110k | } |
1684 | 268k | GF_SAFEALLOC(a, GF_AV1_OBUArrayEntry); |
1685 | 268k | if (!a) break; |
1686 | 268k | a->obu = gf_malloc((size_t)obu_size); |
1687 | 268k | if (!a->obu) { |
1688 | 0 | gf_free(a); |
1689 | 0 | break; |
1690 | 0 | } |
1691 | 268k | gf_bs_seek(bs, pos); |
1692 | 268k | gf_bs_read_data(bs, (char *) a->obu, (u32)obu_size); |
1693 | 268k | a->obu_length = obu_size; |
1694 | 268k | a->obu_type = obu_type; |
1695 | 268k | gf_list_add(cfg->obu_array, a); |
1696 | | |
1697 | 268k | if (size<obu_size) { |
1698 | 827 | GF_LOG(GF_LOG_WARNING, GF_LOG_CODING, ("[AV1] AV1 config misses %d bytes to fit the entire OBU\n", obu_size - size)); |
1699 | 827 | break; |
1700 | 827 | } |
1701 | 267k | size -= (u32) obu_size; |
1702 | 267k | } |
1703 | 43.4k | gf_av1_reset_state(& state, GF_TRUE); |
1704 | 43.4k | gf_bs_align(bs); |
1705 | 43.4k | return cfg; |
1706 | | #else |
1707 | | return NULL; |
1708 | | #endif |
1709 | 46.3k | } |
1710 | | |
1711 | | GF_EXPORT |
1712 | | GF_AV1Config *gf_odf_av1_cfg_read_bs(GF_BitStream *bs) |
1713 | 12.0k | { |
1714 | 12.0k | return gf_odf_av1_cfg_read_bs_size(bs, 0); |
1715 | | |
1716 | 12.0k | } |
1717 | | GF_EXPORT |
1718 | | GF_AV1Config *gf_odf_av1_cfg_read(u8 *dsi, u32 dsi_size) |
1719 | 12.0k | { |
1720 | 12.0k | GF_BitStream *bs = gf_bs_new(dsi, dsi_size, GF_BITSTREAM_READ); |
1721 | 12.0k | GF_AV1Config *cfg = gf_odf_av1_cfg_read_bs(bs); |
1722 | 12.0k | gf_bs_del(bs); |
1723 | 12.0k | return cfg; |
1724 | 12.0k | } |
1725 | | |
1726 | | GF_DOVIDecoderConfigurationRecord *gf_odf_dovi_cfg_read_bs(GF_BitStream *bs) |
1727 | 4.72k | { |
1728 | 4.72k | GF_DOVIDecoderConfigurationRecord *cfg; |
1729 | 4.72k | GF_SAFEALLOC(cfg, GF_DOVIDecoderConfigurationRecord); |
1730 | | |
1731 | 4.72k | cfg->dv_version_major = gf_bs_read_u8(bs); |
1732 | 4.72k | cfg->dv_version_minor = gf_bs_read_u8(bs); |
1733 | 4.72k | cfg->dv_profile = gf_bs_read_int(bs, 7); |
1734 | 4.72k | cfg->dv_level = gf_bs_read_int(bs, 6); |
1735 | 4.72k | cfg->rpu_present_flag = gf_bs_read_int(bs, 1); |
1736 | 4.72k | cfg->el_present_flag = gf_bs_read_int(bs, 1); |
1737 | 4.72k | cfg->bl_present_flag = gf_bs_read_int(bs, 1); |
1738 | 4.72k | cfg->dv_bl_signal_compatibility_id = gf_bs_read_int(bs, 4); |
1739 | 4.72k | if (gf_bs_read_int(bs, 28)) { |
1740 | 0 | GF_LOG(GF_LOG_WARNING, GF_LOG_CODING, ("[DOVI] Configuration reserved bits are not zero\n")); |
1741 | 0 | } |
1742 | 23.6k | for (u32 i=0; i<4; i++) { |
1743 | 18.9k | if (gf_bs_read_u32(bs)) { |
1744 | 0 | GF_LOG(GF_LOG_WARNING, GF_LOG_CODING, ("[DOVII] Configuration reserved bits are not zero\n")); |
1745 | 0 | } |
1746 | 18.9k | } |
1747 | 4.72k | return cfg; |
1748 | 4.72k | } |
1749 | | |
1750 | | GF_EXPORT |
1751 | | void gf_odf_dovi_cfg_del(GF_DOVIDecoderConfigurationRecord *cfg) |
1752 | 4.72k | { |
1753 | 4.72k | gf_free(cfg); |
1754 | 4.72k | } |
1755 | | |
1756 | | GF_Err gf_odf_dovi_cfg_write_bs(GF_DOVIDecoderConfigurationRecord *cfg, GF_BitStream *bs) |
1757 | 0 | { |
1758 | 0 | gf_bs_write_u8(bs, cfg->dv_version_major); |
1759 | 0 | gf_bs_write_u8(bs, cfg->dv_version_minor); |
1760 | 0 | gf_bs_write_int(bs, cfg->dv_profile, 7); |
1761 | 0 | gf_bs_write_int(bs, cfg->dv_level, 6); |
1762 | 0 | gf_bs_write_int(bs, cfg->rpu_present_flag, 1); |
1763 | 0 | gf_bs_write_int(bs, cfg->el_present_flag, 1); |
1764 | 0 | gf_bs_write_int(bs, cfg->bl_present_flag, 1); |
1765 | 0 | gf_bs_write_int(bs, cfg->dv_bl_signal_compatibility_id, 4); |
1766 | 0 | gf_bs_write_int(bs, 0, 28); |
1767 | 0 | gf_bs_write_u32(bs, 0); |
1768 | 0 | gf_bs_write_u32(bs, 0); |
1769 | 0 | gf_bs_write_u32(bs, 0); |
1770 | 0 | gf_bs_write_u32(bs, 0); |
1771 | 0 | return GF_OK; |
1772 | 0 | } |
1773 | | |
1774 | | |
1775 | | GF_Err gf_odf_ac3_cfg_write_bs(GF_AC3Config *cfg, GF_BitStream *bs) |
1776 | 25.4k | { |
1777 | 25.4k | if (!cfg || !bs) return GF_BAD_PARAM; |
1778 | | |
1779 | 25.4k | if (cfg->is_ec3) { |
1780 | 25.4k | u32 i; |
1781 | 25.4k | gf_bs_write_int(bs, cfg->brcode, 13); |
1782 | 25.4k | gf_bs_write_int(bs, cfg->nb_streams - 1, 3); |
1783 | 83.9k | for (i=0; i<cfg->nb_streams; i++) { |
1784 | 58.5k | gf_bs_write_int(bs, cfg->streams[i].fscod, 2); |
1785 | 58.5k | gf_bs_write_int(bs, cfg->streams[i].bsid, 5); |
1786 | 58.5k | gf_bs_write_int(bs, cfg->streams[i].bsmod, 5); |
1787 | 58.5k | gf_bs_write_int(bs, cfg->streams[i].acmod, 3); |
1788 | 58.5k | gf_bs_write_int(bs, cfg->streams[i].lfon, 1); |
1789 | 58.5k | gf_bs_write_int(bs, 0, 3); |
1790 | 58.5k | gf_bs_write_int(bs, cfg->streams[i].nb_dep_sub, 4); |
1791 | 58.5k | if (cfg->streams[i].nb_dep_sub) { |
1792 | 3.70k | gf_bs_write_int(bs, cfg->streams[i].chan_loc, 9); |
1793 | 54.8k | } else { |
1794 | 54.8k | gf_bs_write_int(bs, 0, 1); |
1795 | 54.8k | } |
1796 | 58.5k | } |
1797 | 25.4k | } else { |
1798 | 61 | gf_bs_write_int(bs, cfg->streams[0].fscod, 2); |
1799 | 61 | gf_bs_write_int(bs, cfg->streams[0].bsid, 5); |
1800 | 61 | gf_bs_write_int(bs, cfg->streams[0].bsmod, 3); |
1801 | 61 | gf_bs_write_int(bs, cfg->streams[0].acmod, 3); |
1802 | 61 | gf_bs_write_int(bs, cfg->streams[0].lfon, 1); |
1803 | 61 | gf_bs_write_int(bs, cfg->brcode, 5); |
1804 | 61 | gf_bs_write_int(bs, 0, 5); |
1805 | 61 | } |
1806 | 25.4k | return GF_OK; |
1807 | 25.4k | } |
1808 | | |
1809 | | GF_Err gf_odf_ac3_cfg_write(GF_AC3Config *cfg, u8 **data, u32 *size) |
1810 | 25.4k | { |
1811 | 25.4k | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
1812 | 25.4k | GF_Err e = gf_odf_ac3_cfg_write_bs(cfg, bs); |
1813 | | |
1814 | 25.4k | if (cfg->is_ec3 && (cfg->atmos_ec3_ext || cfg->complexity_index_type)) { |
1815 | 11.4k | gf_bs_write_int(bs, 0, 7); |
1816 | 11.4k | gf_bs_write_int(bs, cfg->atmos_ec3_ext, 1); |
1817 | 11.4k | gf_bs_write_u8(bs, cfg->complexity_index_type); |
1818 | 11.4k | } |
1819 | 25.4k | gf_bs_get_content(bs, data, size); |
1820 | | |
1821 | 25.4k | gf_bs_del(bs); |
1822 | 25.4k | return e; |
1823 | 25.4k | } |
1824 | | |
1825 | | GF_Err gf_odf_ac3_config_parse_bs(GF_BitStream *bs, Bool is_ec3, GF_AC3Config *cfg) |
1826 | 1.03k | { |
1827 | 1.03k | if (!cfg || !bs) return GF_BAD_PARAM; |
1828 | 1.03k | memset(cfg, 0, sizeof(GF_AC3Config)); |
1829 | 1.03k | cfg->is_ec3 = is_ec3; |
1830 | 1.03k | if (is_ec3) { |
1831 | 773 | u32 j; |
1832 | 773 | cfg->is_ec3 = 1; |
1833 | 773 | cfg->brcode = gf_bs_read_int(bs, 13); |
1834 | 773 | cfg->nb_streams = 1 + gf_bs_read_int(bs, 3); |
1835 | 2.12k | for (j=0; j<cfg->nb_streams; j++) { |
1836 | 1.35k | cfg->streams[j].fscod = gf_bs_read_int(bs, 2); |
1837 | 1.35k | cfg->streams[j].bsid = gf_bs_read_int(bs, 5); |
1838 | 1.35k | gf_bs_read_int(bs, 1); |
1839 | 1.35k | cfg->streams[j].asvc = gf_bs_read_int(bs, 1); |
1840 | 1.35k | cfg->streams[j].bsmod = gf_bs_read_int(bs, 3); |
1841 | 1.35k | cfg->streams[j].acmod = gf_bs_read_int(bs, 3); |
1842 | 1.35k | cfg->streams[j].lfon = gf_bs_read_int(bs, 1); |
1843 | 1.35k | gf_bs_read_int(bs, 3); |
1844 | 1.35k | cfg->streams[j].nb_dep_sub = gf_bs_read_int(bs, 4); |
1845 | 1.35k | if (cfg->streams[j].nb_dep_sub) { |
1846 | 579 | cfg->streams[j].chan_loc = gf_bs_read_int(bs, 9); |
1847 | 771 | } else { |
1848 | 771 | gf_bs_read_int(bs, 1); |
1849 | 771 | } |
1850 | 1.35k | } |
1851 | 773 | } else { |
1852 | 266 | cfg->nb_streams = 1; |
1853 | 266 | cfg->streams[0].fscod = gf_bs_read_int(bs, 2); |
1854 | 266 | cfg->streams[0].bsid = gf_bs_read_int(bs, 5); |
1855 | 266 | cfg->streams[0].bsmod = gf_bs_read_int(bs, 3); |
1856 | 266 | cfg->streams[0].acmod = gf_bs_read_int(bs, 3); |
1857 | 266 | cfg->streams[0].lfon = gf_bs_read_int(bs, 1); |
1858 | 266 | cfg->brcode = gf_bs_read_int(bs, 5); |
1859 | 266 | gf_bs_read_int(bs, 5); |
1860 | 266 | } |
1861 | 1.03k | return GF_OK; |
1862 | 1.03k | } |
1863 | | |
1864 | | GF_Err gf_odf_ac3_config_parse(u8 *dsi, u32 dsi_len, Bool is_ec3, GF_AC3Config *cfg) |
1865 | 0 | { |
1866 | 0 | GF_BitStream *bs; |
1867 | 0 | GF_Err e; |
1868 | 0 | if (!cfg || !dsi) return GF_BAD_PARAM; |
1869 | 0 | bs = gf_bs_new(dsi, dsi_len, GF_BITSTREAM_READ); |
1870 | 0 | e = gf_odf_ac3_config_parse_bs(bs, is_ec3, cfg); |
1871 | 0 | if (is_ec3 && gf_bs_available(bs)>=2) { |
1872 | 0 | gf_bs_read_int(bs, 7); |
1873 | 0 | cfg->atmos_ec3_ext = gf_bs_read_int(bs, 1); |
1874 | 0 | cfg->complexity_index_type = gf_bs_read_u8(bs); |
1875 | 0 | } |
1876 | 0 | gf_bs_del(bs); |
1877 | 0 | return e; |
1878 | 0 | } |
1879 | | |
1880 | | |
1881 | | GF_Err gf_odf_opus_cfg_parse_bs(GF_BitStream *bs, GF_OpusConfig *cfg) |
1882 | 157 | { |
1883 | 157 | memset(cfg, 0, sizeof(GF_OpusConfig)); |
1884 | 157 | cfg->version = gf_bs_read_u8(bs); |
1885 | 157 | cfg->OutputChannelCount = gf_bs_read_u8(bs); |
1886 | 157 | cfg->PreSkip = gf_bs_read_u16_le(bs); |
1887 | 157 | cfg->InputSampleRate = gf_bs_read_u32_le(bs); |
1888 | 157 | cfg->OutputGain = gf_bs_read_u16_le(bs); |
1889 | 157 | cfg->ChannelMappingFamily = gf_bs_read_u8(bs); |
1890 | 157 | if (cfg->ChannelMappingFamily) { |
1891 | 4 | cfg->StreamCount = gf_bs_read_u8(bs); |
1892 | 4 | cfg->CoupledCount = gf_bs_read_u8(bs); |
1893 | 4 | gf_bs_read_data(bs, (char *) cfg->ChannelMapping, cfg->OutputChannelCount); |
1894 | 4 | } |
1895 | 157 | return GF_OK; |
1896 | 157 | } |
1897 | | GF_Err gf_odf_opus_cfg_parse(u8 *dsi, u32 dsi_len, GF_OpusConfig *cfg) |
1898 | 157 | { |
1899 | 157 | GF_BitStream *bs; |
1900 | 157 | GF_Err e; |
1901 | 157 | if (!cfg || !dsi) return GF_BAD_PARAM; |
1902 | 157 | bs = gf_bs_new(dsi, dsi_len, GF_BITSTREAM_READ); |
1903 | 157 | e = gf_odf_opus_cfg_parse_bs(bs, cfg); |
1904 | 157 | gf_bs_del(bs); |
1905 | 157 | return e; |
1906 | 157 | } |
1907 | | |
1908 | | GF_Err gf_odf_opus_cfg_write_bs(GF_OpusConfig *cfg, GF_BitStream *bs) |
1909 | 151 | { |
1910 | 151 | if (!cfg || !bs) return GF_BAD_PARAM; |
1911 | 151 | gf_bs_write_u8(bs, cfg->version); |
1912 | 151 | gf_bs_write_u8(bs, cfg->OutputChannelCount); |
1913 | 151 | gf_bs_write_u16_le(bs, cfg->PreSkip); |
1914 | 151 | gf_bs_write_u32_le(bs, cfg->InputSampleRate); |
1915 | 151 | gf_bs_write_u16_le(bs, cfg->OutputGain); |
1916 | 151 | gf_bs_write_u8(bs, cfg->ChannelMappingFamily); |
1917 | 151 | if (cfg->ChannelMappingFamily) { |
1918 | 4 | gf_bs_write_u8(bs, cfg->StreamCount); |
1919 | 4 | gf_bs_write_u8(bs, cfg->CoupledCount); |
1920 | 4 | gf_bs_write_data(bs, (char *) cfg->ChannelMapping, cfg->OutputChannelCount); |
1921 | 4 | } |
1922 | 151 | return GF_OK; |
1923 | 151 | } |
1924 | | |
1925 | | GF_Err gf_odf_opus_cfg_write(GF_OpusConfig *cfg, u8 **data, u32 *size) |
1926 | 0 | { |
1927 | 0 | GF_BitStream *bs = gf_bs_new(NULL, 0, GF_BITSTREAM_WRITE); |
1928 | 0 | GF_Err e = gf_odf_opus_cfg_write_bs(cfg, bs); |
1929 | |
|
1930 | 0 | gf_bs_get_content(bs, data, size); |
1931 | 0 | gf_bs_del(bs); |
1932 | 0 | return e; |
1933 | 0 | } |