1 /*
2 * GPAC - Multimedia Framework C SDK
3 *
4 * Authors: Jean Le Feuvre
5 * Copyright (c) Telecom ParisTech 2000-2012
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/utf.h>
28
29 #define DATE_CODING_BIT_LEN 40
30
31 #ifndef GPAC_MINIMAL_ODF
32
OD_ReadUTF8String(GF_BitStream * bs,char ** string,Bool isUTF8,u32 * read)33 static GFINLINE GF_Err OD_ReadUTF8String(GF_BitStream *bs, char **string, Bool isUTF8, u32 *read)
34 {
35 u32 len;
36 *read = 1;
37 len = gf_bs_read_int(bs, 8) + 1;
38 if (!isUTF8) len *= 2;
39 (*string) = (char *)gf_malloc(sizeof(char)*len);
40 if (!(*string)) return GF_OUT_OF_MEM;
41 gf_bs_read_data(bs, (*string), len);
42 *read += len;
43 return GF_OK;
44 }
45
OD_SizeUTF8String(char * string,Bool isUTF8)46 static GFINLINE u32 OD_SizeUTF8String(char *string, Bool isUTF8)
47 {
48 if (isUTF8) return 1 + (u32)strlen(string);
49 return 1 + 2 * (u32)gf_utf8_wcslen((const unsigned short *)string);
50 }
51
OD_WriteUTF8String(GF_BitStream * bs,char * string,Bool isUTF8)52 static GFINLINE void OD_WriteUTF8String(GF_BitStream *bs, char *string, Bool isUTF8)
53 {
54 u32 len;
55 if (isUTF8) {
56 len = (u32)strlen(string);
57 gf_bs_write_int(bs, len, 8);
58 gf_bs_write_data(bs, string, len);
59 }
60 else {
61 len = (u32)gf_utf8_wcslen((const unsigned short *)string);
62 gf_bs_write_int(bs, len, 8);
63 gf_bs_write_data(bs, string, len * 2);
64 }
65 }
66
67 #endif // GPAC_MINIMAL_ODF
68
69 /*use to parse strings read the length as well - Warning : the alloc is done here !!*/
gf_odf_read_url_string(GF_BitStream * bs,char ** string,u32 * readBytes)70 GF_Err gf_odf_read_url_string(GF_BitStream *bs, char **string, u32 *readBytes)
71 {
72 u32 length;
73 *readBytes = 0;
74
75 /*if the string is not NULL, return an error...*/
76 if (*string != NULL) return GF_BAD_PARAM;
77
78 /*the len is always on 8 bits*/
79 length = gf_bs_read_int(bs, 8);
80 *readBytes = 1;
81 /*JLF AMD to MPEG-4 systems :) - This is not conformant at all, just hoping MPEG will accept it soon
82 since 255bytes URL is a real pain in the neck*/
83 if (!length) {
84 length = gf_bs_read_int(bs, 32);
85 *readBytes += 4;
86 }
87
88 /*we want to use strlen to get rid of "stringLength" => we need an extra 0*/
89 (*string) = (char *)gf_malloc(length + 1);
90 if (!string) return GF_OUT_OF_MEM;
91 gf_bs_read_data(bs, (*string), length);
92 *readBytes += length;
93 (*string)[length] = 0;
94 return GF_OK;
95 }
96
97 /*writes string*/
gf_odf_write_url_string(GF_BitStream * bs,char * string)98 GF_Err gf_odf_write_url_string(GF_BitStream *bs, char *string)
99 {
100 u32 len;
101 /*we accept NULL strings now*/
102 if (!string) {
103 gf_bs_write_int(bs, 0, 8);
104 return GF_OK;
105 }
106 len = (u32)strlen(string);
107 if (len > 255) {
108 gf_bs_write_int(bs, 0, 8);
109 gf_bs_write_int(bs, len, 32);
110 }
111 else {
112 gf_bs_write_int(bs, len, 8);
113 }
114 gf_bs_write_data(bs, string, len);
115 return GF_OK;
116 }
117
gf_odf_size_url_string(char * string)118 u32 gf_odf_size_url_string(char *string)
119 {
120 u32 len = (u32)strlen(string);
121 if (len>255) return len + 5;
122 return len + 1;
123 }
124
gf_odf_new_esd()125 GF_Descriptor *gf_odf_new_esd()
126 {
127 GF_ESD *newDesc = (GF_ESD *)gf_malloc(sizeof(GF_ESD));
128 if (!newDesc) return NULL;
129 memset(newDesc, 0, sizeof(GF_ESD));
130 newDesc->IPIDataSet = gf_list_new();
131 newDesc->IPMPDescriptorPointers = gf_list_new();
132 newDesc->extensionDescriptors = gf_list_new();
133 newDesc->tag = GF_ODF_ESD_TAG;
134 return (GF_Descriptor *)newDesc;
135 }
136
137
gf_odf_del_esd(GF_ESD * esd)138 GF_Err gf_odf_del_esd(GF_ESD *esd)
139 {
140 GF_Err e;
141 if (!esd) return GF_BAD_PARAM;
142 if (esd->URLString) gf_free(esd->URLString);
143
144 if (esd->decoderConfig) {
145 e = gf_odf_delete_descriptor((GF_Descriptor *)esd->decoderConfig);
146 if (e) return e;
147 }
148 if (esd->slConfig) {
149 e = gf_odf_delete_descriptor((GF_Descriptor *)esd->slConfig);
150 if (e) return e;
151 }
152 if (esd->ipiPtr) {
153 e = gf_odf_delete_descriptor((GF_Descriptor *)esd->ipiPtr);
154 if (e) return e;
155 }
156 if (esd->qos) {
157 e = gf_odf_delete_descriptor((GF_Descriptor *)esd->qos);
158 if (e) return e;
159 }
160 if (esd->RegDescriptor) {
161 e = gf_odf_delete_descriptor((GF_Descriptor *)esd->RegDescriptor);
162 if (e) return e;
163 }
164 if (esd->langDesc) {
165 e = gf_odf_delete_descriptor((GF_Descriptor *)esd->langDesc);
166 if (e) return e;
167 }
168
169 e = gf_odf_delete_descriptor_list(esd->IPIDataSet);
170 if (e) return e;
171 e = gf_odf_delete_descriptor_list(esd->IPMPDescriptorPointers);
172 if (e) return e;
173 e = gf_odf_delete_descriptor_list(esd->extensionDescriptors);
174 if (e) return e;
175 gf_free(esd);
176 return GF_OK;
177 }
178
179
AddDescriptorToESD(GF_ESD * esd,GF_Descriptor * desc)180 GF_Err AddDescriptorToESD(GF_ESD *esd, GF_Descriptor *desc)
181 {
182 if (!esd || !desc) return GF_BAD_PARAM;
183
184 switch (desc->tag) {
185 case GF_ODF_DCD_TAG:
186 if (esd->decoderConfig) return GF_ODF_INVALID_DESCRIPTOR;
187 esd->decoderConfig = (GF_DecoderConfig *)desc;
188 break;
189
190 case GF_ODF_SLC_TAG:
191 if (esd->slConfig) return GF_ODF_INVALID_DESCRIPTOR;
192 esd->slConfig = (GF_SLConfig *)desc;
193 break;
194
195 case GF_ODF_MUXINFO_TAG:
196 gf_list_add(esd->extensionDescriptors, desc);
197 break;
198
199 case GF_ODF_LANG_TAG:
200 if (esd->langDesc) return GF_ODF_INVALID_DESCRIPTOR;
201 esd->langDesc = (GF_Language *)desc;
202 break;
203
204 #ifndef GPAC_MINIMAL_ODF
205 //the GF_ODF_ISOM_IPI_PTR_TAG is only used in the file format and replaces GF_ODF_IPI_PTR_TAG...
206 case GF_ODF_ISOM_IPI_PTR_TAG:
207 case GF_ODF_IPI_PTR_TAG:
208 if (esd->ipiPtr) return GF_ODF_INVALID_DESCRIPTOR;
209 esd->ipiPtr = (GF_IPIPtr *)desc;
210 break;
211
212 case GF_ODF_QOS_TAG:
213 if (esd->qos) return GF_ODF_INVALID_DESCRIPTOR;
214 esd->qos = (GF_QoS_Descriptor *)desc;
215 break;
216
217 case GF_ODF_CI_TAG:
218 case GF_ODF_SCI_TAG:
219 return gf_list_add(esd->IPIDataSet, desc);
220
221 //we use the same struct for v1 and v2 IPMP DPs
222 case GF_ODF_IPMP_PTR_TAG:
223 return gf_list_add(esd->IPMPDescriptorPointers, desc);
224
225 case GF_ODF_REG_TAG:
226 if (esd->RegDescriptor) return GF_ODF_INVALID_DESCRIPTOR;
227 esd->RegDescriptor = (GF_Registration *)desc;
228 break;
229 #endif
230
231 default:
232 if ((desc->tag >= GF_ODF_EXT_BEGIN_TAG) &&
233 (desc->tag <= GF_ODF_EXT_END_TAG)) {
234 return gf_list_add(esd->extensionDescriptors, desc);
235 }
236 gf_odf_delete_descriptor(desc);
237 return GF_OK;
238 }
239
240 return GF_OK;
241 }
242
gf_odf_read_esd(GF_BitStream * bs,GF_ESD * esd,u32 DescSize)243 GF_Err gf_odf_read_esd(GF_BitStream *bs, GF_ESD *esd, u32 DescSize)
244 {
245 GF_Err e = GF_OK;
246 u32 ocrflag, urlflag, streamdependflag, tmp_size, nbBytes, read;
247
248 if (!esd) return GF_BAD_PARAM;
249
250 nbBytes = 0;
251
252 esd->ESID = gf_bs_read_int(bs, 16);
253 streamdependflag = gf_bs_read_int(bs, 1);
254 urlflag = gf_bs_read_int(bs, 1);
255 ocrflag = gf_bs_read_int(bs, 1);
256 esd->streamPriority = gf_bs_read_int(bs, 5);
257 nbBytes += 3;
258
259 if (streamdependflag) {
260 esd->dependsOnESID = gf_bs_read_int(bs, 16);
261 nbBytes += 2;
262 }
263
264 if (urlflag) {
265 e = gf_odf_read_url_string(bs, &esd->URLString, &read);
266 if (e) return e;
267 nbBytes += read;
268 }
269 if (ocrflag) {
270 esd->OCRESID = gf_bs_read_int(bs, 16);
271 nbBytes += 2;
272 }
273 /*fix broken sync*/
274 // if (esd->OCRESID == esd->ESID) esd->OCRESID = 0;
275
276 while (nbBytes < DescSize) {
277 GF_Descriptor *tmp = NULL;
278 e = gf_odf_parse_descriptor(bs, &tmp, &tmp_size);
279 /*fix for iPod files*/
280 if (e == GF_ODF_INVALID_DESCRIPTOR) {
281 nbBytes += tmp_size;
282 if (nbBytes>DescSize) return e;
283 gf_bs_read_int(bs, DescSize - nbBytes);
284 return GF_OK;
285 }
286 if (e) return e;
287 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
288 e = AddDescriptorToESD(esd, tmp);
289 if (e) return e;
290 nbBytes += tmp_size + gf_odf_size_field_size(tmp_size);
291
292 //apple fix
293 if (!tmp_size) nbBytes = DescSize;
294
295 }
296 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
297 return e;
298
299 }
300
gf_odf_size_esd(GF_ESD * esd,u32 * outSize)301 GF_Err gf_odf_size_esd(GF_ESD *esd, u32 *outSize)
302 {
303 GF_Err e;
304 u32 tmpSize;
305 if (!esd) return GF_BAD_PARAM;
306
307 *outSize = 0;
308 *outSize += 3;
309
310 /*this helps keeping proper sync: some people argue that OCR_ES_ID == ES_ID is a circular reference
311 of streams. Since this is equivalent to no OCR_ES_ID, keep it that way*/
312 // if (esd->OCRESID == esd->ESID) esd->OCRESID = 0;
313
314 if (esd->dependsOnESID) *outSize += 2;
315 if (esd->URLString) *outSize += gf_odf_size_url_string(esd->URLString);
316 if (esd->OCRESID) *outSize += 2;
317
318 if (esd->decoderConfig) {
319 e = gf_odf_size_descriptor((GF_Descriptor *)esd->decoderConfig, &tmpSize);
320 if (e) return e;
321 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
322 }
323 if (esd->slConfig) {
324 e = gf_odf_size_descriptor((GF_Descriptor *)esd->slConfig, &tmpSize);
325 if (e) return e;
326 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
327 }
328 if (esd->ipiPtr) {
329 e = gf_odf_size_descriptor((GF_Descriptor *)esd->ipiPtr, &tmpSize);
330 if (e) return e;
331 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
332 }
333 if (esd->langDesc) {
334 e = gf_odf_size_descriptor((GF_Descriptor *)esd->langDesc, &tmpSize);
335 if (e) return e;
336 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
337 }
338
339 e = gf_odf_size_descriptor_list(esd->IPIDataSet, outSize);
340 if (e) return e;
341 e = gf_odf_size_descriptor_list(esd->IPMPDescriptorPointers, outSize);
342 if (e) return e;
343 if (esd->qos) {
344 e = gf_odf_size_descriptor((GF_Descriptor *)esd->qos, &tmpSize);
345 if (e) return e;
346 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
347 }
348 if (esd->RegDescriptor) {
349 e = gf_odf_size_descriptor((GF_Descriptor *)esd->RegDescriptor, &tmpSize);
350 if (e) return e;
351 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
352 }
353 return gf_odf_size_descriptor_list(esd->extensionDescriptors, outSize);
354 }
355
gf_odf_write_esd(GF_BitStream * bs,GF_ESD * esd)356 GF_Err gf_odf_write_esd(GF_BitStream *bs, GF_ESD *esd)
357 {
358 GF_Err e;
359 u32 size;
360 if (!esd) return GF_BAD_PARAM;
361
362 e = gf_odf_size_descriptor((GF_Descriptor *)esd, &size);
363 if (e) return e;
364 e = gf_odf_write_base_descriptor(bs, esd->tag, size);
365 if (e) return e;
366
367 gf_bs_write_int(bs, esd->ESID, 16);
368 gf_bs_write_int(bs, esd->dependsOnESID ? 1 : 0, 1);
369 gf_bs_write_int(bs, esd->URLString != NULL ? 1 : 0, 1);
370 gf_bs_write_int(bs, esd->OCRESID ? 1 : 0, 1);
371 gf_bs_write_int(bs, esd->streamPriority, 5);
372
373 if (esd->dependsOnESID) {
374 gf_bs_write_int(bs, esd->dependsOnESID, 16);
375 }
376 if (esd->URLString) {
377 e = gf_odf_write_url_string(bs, esd->URLString);
378 if (e) return e;
379 }
380
381
382 if (esd->OCRESID) {
383 gf_bs_write_int(bs, esd->OCRESID, 16);
384 }
385 if (esd->decoderConfig) {
386 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)esd->decoderConfig);
387 if (e) return e;
388 }
389 if (esd->slConfig) {
390 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)esd->slConfig);
391 if (e) return e;
392 }
393 if (esd->ipiPtr) {
394 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)esd->ipiPtr);
395 if (e) return e;
396 }
397 if (esd->langDesc) {
398 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)esd->langDesc);
399 if (e) return e;
400 }
401
402 e = gf_odf_write_descriptor_list(bs, esd->IPIDataSet);
403 if (e) return e;
404 e = gf_odf_write_descriptor_list(bs, esd->IPMPDescriptorPointers);
405 if (e) return e;
406 if (esd->qos) {
407 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)esd->qos);
408 if (e) return e;
409 }
410 if (esd->RegDescriptor) {
411 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)esd->RegDescriptor);
412 if (e) return e;
413 }
414 return gf_odf_write_descriptor_list(bs, esd->extensionDescriptors);
415 }
416
gf_odf_new_iod()417 GF_Descriptor *gf_odf_new_iod()
418 {
419 GF_InitialObjectDescriptor *newDesc = (GF_InitialObjectDescriptor *)gf_malloc(sizeof(GF_InitialObjectDescriptor));
420 if (!newDesc) return NULL;
421 memset(newDesc, 0, sizeof(GF_InitialObjectDescriptor));
422
423 newDesc->ESDescriptors = gf_list_new();
424 newDesc->OCIDescriptors = gf_list_new();
425 newDesc->IPMP_Descriptors = gf_list_new();
426
427 newDesc->extensionDescriptors = gf_list_new();
428 newDesc->tag = GF_ODF_IOD_TAG;
429 return (GF_Descriptor *)newDesc;
430 }
431
gf_odf_del_iod(GF_InitialObjectDescriptor * iod)432 GF_Err gf_odf_del_iod(GF_InitialObjectDescriptor *iod)
433 {
434 GF_Err e;
435 if (!iod) return GF_BAD_PARAM;
436 if (iod->URLString) gf_free(iod->URLString);
437 e = gf_odf_delete_descriptor_list(iod->ESDescriptors);
438 if (e) return e;
439 e = gf_odf_delete_descriptor_list(iod->OCIDescriptors);
440 if (e) return e;
441 e = gf_odf_delete_descriptor_list(iod->IPMP_Descriptors);
442 if (e) return e;
443 e = gf_odf_delete_descriptor_list(iod->extensionDescriptors);
444 if (e) return e;
445 if (iod->IPMPToolList) gf_odf_delete_descriptor((GF_Descriptor *)iod->IPMPToolList);
446 gf_free(iod);
447 return GF_OK;
448 }
449
AddDescriptorToIOD(GF_InitialObjectDescriptor * iod,GF_Descriptor * desc)450 GF_Err AddDescriptorToIOD(GF_InitialObjectDescriptor *iod, GF_Descriptor *desc)
451 {
452 if (!iod || !desc) return GF_BAD_PARAM;
453
454 switch (desc->tag) {
455 case GF_ODF_ESD_TAG:
456 return gf_list_add(iod->ESDescriptors, desc);
457
458 //we use the same struct for v1 and v2 IPMP DPs
459 case GF_ODF_IPMP_PTR_TAG:
460 /*IPMPX*/
461 case GF_ODF_IPMP_TAG:
462 return gf_list_add(iod->IPMP_Descriptors, desc);
463
464 /*IPMPX*/
465 case GF_ODF_IPMP_TL_TAG:
466 if (iod->IPMPToolList) gf_odf_desc_del((GF_Descriptor *)iod->IPMPToolList);
467 iod->IPMPToolList = (GF_IPMP_ToolList *)desc;
468 return GF_OK;
469
470 default:
471 break;
472 }
473 if ((desc->tag >= GF_ODF_OCI_BEGIN_TAG) && (desc->tag <= GF_ODF_OCI_END_TAG)) return gf_list_add(iod->OCIDescriptors, desc);
474 if ((desc->tag >= GF_ODF_EXT_BEGIN_TAG) && (desc->tag <= GF_ODF_EXT_END_TAG)) return gf_list_add(iod->extensionDescriptors, desc);
475 return GF_BAD_PARAM;
476 }
477
gf_odf_read_iod(GF_BitStream * bs,GF_InitialObjectDescriptor * iod,u32 DescSize)478 GF_Err gf_odf_read_iod(GF_BitStream *bs, GF_InitialObjectDescriptor *iod, u32 DescSize)
479 {
480 GF_Err e;
481 u32 urlflag, read;
482 u32 tmp_size, nbBytes = 0;
483 if (!iod) return GF_BAD_PARAM;
484
485 iod->objectDescriptorID = gf_bs_read_int(bs, 10);
486 urlflag = gf_bs_read_int(bs, 1);
487 iod->inlineProfileFlag = gf_bs_read_int(bs, 1);
488 /*reserved = */gf_bs_read_int(bs, 4);
489 nbBytes += 2;
490
491 if (urlflag) {
492 e = gf_odf_read_url_string(bs, &iod->URLString, &read);
493 if (e) return e;
494 nbBytes += read;
495 }
496 else {
497 iod->OD_profileAndLevel = gf_bs_read_int(bs, 8);
498 iod->scene_profileAndLevel = gf_bs_read_int(bs, 8);
499 iod->audio_profileAndLevel = gf_bs_read_int(bs, 8);
500 iod->visual_profileAndLevel = gf_bs_read_int(bs, 8);
501 iod->graphics_profileAndLevel = gf_bs_read_int(bs, 8);
502 nbBytes += 5;
503 }
504
505 while (nbBytes < DescSize) {
506 GF_Descriptor *tmp = NULL;
507 e = gf_odf_parse_descriptor(bs, &tmp, &tmp_size);
508 if (e) return e;
509 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
510 e = AddDescriptorToIOD(iod, tmp);
511 if (e) return e;
512 nbBytes += tmp_size + gf_odf_size_field_size(tmp_size);
513 }
514 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
515 return GF_OK;
516 }
517
gf_odf_size_iod(GF_InitialObjectDescriptor * iod,u32 * outSize)518 GF_Err gf_odf_size_iod(GF_InitialObjectDescriptor *iod, u32 *outSize)
519 {
520 GF_Err e;
521 if (!iod) return GF_BAD_PARAM;
522
523 *outSize = 0;
524 *outSize += 2;
525 if (iod->URLString) {
526 *outSize += gf_odf_size_url_string(iod->URLString);
527 }
528 else {
529 *outSize += 5;
530 e = gf_odf_size_descriptor_list(iod->ESDescriptors, outSize);
531 if (e) return e;
532 e = gf_odf_size_descriptor_list(iod->OCIDescriptors, outSize);
533 if (e) return e;
534 e = gf_odf_size_descriptor_list(iod->IPMP_Descriptors, outSize);
535 if (e) return e;
536
537 }
538 e = gf_odf_size_descriptor_list(iod->extensionDescriptors, outSize);
539 if (e) return e;
540 if (iod->IPMPToolList) {
541 u32 tmpSize;
542 e = gf_odf_size_descriptor((GF_Descriptor *)iod->IPMPToolList, &tmpSize);
543 if (e) return e;
544 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
545 }
546 return GF_OK;
547 }
548
gf_odf_write_iod(GF_BitStream * bs,GF_InitialObjectDescriptor * iod)549 GF_Err gf_odf_write_iod(GF_BitStream *bs, GF_InitialObjectDescriptor *iod)
550 {
551 GF_Err e;
552 u32 size;
553 if (!iod) return GF_BAD_PARAM;
554
555 e = gf_odf_size_descriptor((GF_Descriptor *)iod, &size);
556 if (e) return e;
557 e = gf_odf_write_base_descriptor(bs, iod->tag, size);
558 if (e) return e;
559
560 gf_bs_write_int(bs, iod->objectDescriptorID, 10);
561 gf_bs_write_int(bs, iod->URLString != NULL ? 1 : 0, 1);
562 gf_bs_write_int(bs, iod->inlineProfileFlag, 1);
563 gf_bs_write_int(bs, 15, 4); //reserved: 0b1111 == 15
564
565 if (iod->URLString) {
566 gf_odf_write_url_string(bs, iod->URLString);
567 }
568 else {
569 gf_bs_write_int(bs, iod->OD_profileAndLevel, 8);
570 gf_bs_write_int(bs, iod->scene_profileAndLevel, 8);
571 gf_bs_write_int(bs, iod->audio_profileAndLevel, 8);
572 gf_bs_write_int(bs, iod->visual_profileAndLevel, 8);
573 gf_bs_write_int(bs, iod->graphics_profileAndLevel, 8);
574 e = gf_odf_write_descriptor_list(bs, iod->ESDescriptors);
575 if (e) return e;
576 e = gf_odf_write_descriptor_list(bs, iod->OCIDescriptors);
577 if (e) return e;
578 e = gf_odf_write_descriptor_list_filter(bs, iod->IPMP_Descriptors, GF_ODF_IPMP_PTR_TAG);
579 if (e) return e;
580 e = gf_odf_write_descriptor_list_filter(bs, iod->IPMP_Descriptors, GF_ODF_IPMP_TAG);
581 if (e) return e;
582 if (iod->IPMPToolList) {
583 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)iod->IPMPToolList);
584 if (e) return e;
585 }
586 }
587 return gf_odf_write_descriptor_list(bs, iod->extensionDescriptors);
588 }
589
590
591
gf_odf_new_od()592 GF_Descriptor *gf_odf_new_od()
593 {
594 GF_ObjectDescriptor *newDesc;
595 GF_SAFEALLOC(newDesc, GF_ObjectDescriptor);
596 if (!newDesc) return NULL;
597
598 newDesc->URLString = NULL;
599 newDesc->ESDescriptors = gf_list_new();
600 newDesc->OCIDescriptors = gf_list_new();
601 newDesc->IPMP_Descriptors = gf_list_new();
602 newDesc->extensionDescriptors = gf_list_new();
603 newDesc->objectDescriptorID = 0;
604 newDesc->tag = GF_ODF_OD_TAG;
605 return (GF_Descriptor *)newDesc;
606 }
607
gf_odf_del_od(GF_ObjectDescriptor * od)608 GF_Err gf_odf_del_od(GF_ObjectDescriptor *od)
609 {
610 GF_Err e;
611 if (!od) return GF_BAD_PARAM;
612 if (od->URLString) gf_free(od->URLString);
613 e = gf_odf_delete_descriptor_list(od->ESDescriptors);
614 if (e) return e;
615 e = gf_odf_delete_descriptor_list(od->OCIDescriptors);
616 if (e) return e;
617 e = gf_odf_delete_descriptor_list(od->IPMP_Descriptors);
618 if (e) return e;
619 e = gf_odf_delete_descriptor_list(od->extensionDescriptors);
620 if (e) return e;
621 gf_free(od);
622 return GF_OK;
623 }
624
AddDescriptorToOD(GF_ObjectDescriptor * od,GF_Descriptor * desc)625 GF_Err AddDescriptorToOD(GF_ObjectDescriptor *od, GF_Descriptor *desc)
626 {
627 if (!od || !desc) return GF_BAD_PARAM;
628
629 //check if we can handle ContentClassif tags
630 if ((desc->tag >= GF_ODF_OCI_BEGIN_TAG) &&
631 (desc->tag <= GF_ODF_OCI_END_TAG)) {
632 return gf_list_add(od->OCIDescriptors, desc);
633 }
634
635 //or extensions
636 if ((desc->tag >= GF_ODF_EXT_BEGIN_TAG) &&
637 (desc->tag <= GF_ODF_EXT_END_TAG)) {
638 return gf_list_add(od->extensionDescriptors, desc);
639 }
640
641 //to cope with envivio
642 switch (desc->tag) {
643 case GF_ODF_ESD_TAG:
644 case GF_ODF_ESD_REF_TAG:
645 return gf_list_add(od->ESDescriptors, desc);
646
647 //we use the same struct for v1 and v2 IPMP DPs
648 case GF_ODF_IPMP_PTR_TAG:
649 case GF_ODF_IPMP_TAG:
650 return gf_list_add(od->IPMP_Descriptors, desc);
651
652 default:
653 return GF_BAD_PARAM;
654 }
655 }
656
gf_odf_read_od(GF_BitStream * bs,GF_ObjectDescriptor * od,u32 DescSize)657 GF_Err gf_odf_read_od(GF_BitStream *bs, GF_ObjectDescriptor *od, u32 DescSize)
658 {
659 GF_Err e;
660 u32 urlflag;
661 u32 tmpSize, nbBytes = 0;
662 if (!od) return GF_BAD_PARAM;
663
664 od->objectDescriptorID = gf_bs_read_int(bs, 10);
665 urlflag = gf_bs_read_int(bs, 1);
666 /*reserved = */gf_bs_read_int(bs, 5);
667 nbBytes += 2;
668
669 if (urlflag) {
670 u32 read;
671 e = gf_odf_read_url_string(bs, &od->URLString, &read);
672 if (e) return e;
673 nbBytes += read;
674 }
675
676 while (nbBytes < DescSize) {
677 GF_Descriptor *tmp = NULL;
678 e = gf_odf_parse_descriptor(bs, &tmp, &tmpSize);
679 if (e) return e;
680 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
681 e = AddDescriptorToOD(od, tmp);
682 if (e) return e;
683 nbBytes += tmpSize + gf_odf_size_field_size(tmpSize);
684 }
685 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
686 return GF_OK;
687 }
688
gf_odf_size_od(GF_ObjectDescriptor * od,u32 * outSize)689 GF_Err gf_odf_size_od(GF_ObjectDescriptor *od, u32 *outSize)
690 {
691 GF_Err e;
692 if (!od) return GF_BAD_PARAM;
693
694 *outSize = 2;
695 if (od->URLString) {
696 *outSize += gf_odf_size_url_string(od->URLString);
697 }
698 else {
699 e = gf_odf_size_descriptor_list(od->ESDescriptors, outSize);
700 if (e) return e;
701 e = gf_odf_size_descriptor_list(od->OCIDescriptors, outSize);
702 if (e) return e;
703 e = gf_odf_size_descriptor_list(od->IPMP_Descriptors, outSize);
704 if (e) return e;
705 }
706 return gf_odf_size_descriptor_list(od->extensionDescriptors, outSize);
707 }
708
gf_odf_write_od(GF_BitStream * bs,GF_ObjectDescriptor * od)709 GF_Err gf_odf_write_od(GF_BitStream *bs, GF_ObjectDescriptor *od)
710 {
711 GF_Err e;
712 u32 size;
713 if (!od) return GF_BAD_PARAM;
714
715 e = gf_odf_size_descriptor((GF_Descriptor *)od, &size);
716 if (e) return e;
717 e = gf_odf_write_base_descriptor(bs, od->tag, size);
718 if (e) return e;
719
720 gf_bs_write_int(bs, od->objectDescriptorID, 10);
721 gf_bs_write_int(bs, od->URLString != NULL ? 1 : 0, 1);
722 gf_bs_write_int(bs, 31, 5); //reserved: 0b1111.1 == 31
723
724 if (od->URLString) {
725 gf_odf_write_url_string(bs, od->URLString);
726 }
727 else {
728 e = gf_odf_write_descriptor_list(bs, od->ESDescriptors);
729 if (e) return e;
730 e = gf_odf_write_descriptor_list(bs, od->OCIDescriptors);
731 if (e) return e;
732 e = gf_odf_write_descriptor_list_filter(bs, od->IPMP_Descriptors, GF_ODF_IPMP_PTR_TAG);
733 if (e) return e;
734 e = gf_odf_write_descriptor_list_filter(bs, od->IPMP_Descriptors, GF_ODF_IPMP_TAG);
735 if (e) return e;
736 }
737 return gf_odf_write_descriptor_list(bs, od->extensionDescriptors);
738 }
739
gf_odf_new_isom_iod()740 GF_Descriptor *gf_odf_new_isom_iod()
741 {
742 GF_IsomInitialObjectDescriptor *newDesc = (GF_IsomInitialObjectDescriptor *)gf_malloc(sizeof(GF_IsomInitialObjectDescriptor));
743 if (!newDesc) return NULL;
744 memset(newDesc, 0, sizeof(GF_IsomInitialObjectDescriptor));
745
746 newDesc->ES_ID_IncDescriptors = gf_list_new();
747 newDesc->ES_ID_RefDescriptors = gf_list_new();
748 newDesc->OCIDescriptors = gf_list_new();
749 newDesc->IPMP_Descriptors = gf_list_new();
750 newDesc->extensionDescriptors = gf_list_new();
751 newDesc->tag = GF_ODF_ISOM_IOD_TAG;
752
753 //by default create an IOD with no inline and no capabilities
754 newDesc->audio_profileAndLevel = 0xFF;
755 newDesc->graphics_profileAndLevel = 0xFF;
756 newDesc->scene_profileAndLevel = 0xFF;
757 newDesc->OD_profileAndLevel = 0xFF;
758 newDesc->visual_profileAndLevel = 0xFF;
759 return (GF_Descriptor *)newDesc;
760 }
761
gf_odf_del_isom_iod(GF_IsomInitialObjectDescriptor * iod)762 GF_Err gf_odf_del_isom_iod(GF_IsomInitialObjectDescriptor *iod)
763 {
764 GF_Err e;
765 if (!iod) return GF_BAD_PARAM;
766 if (iod->URLString) gf_free(iod->URLString);
767 e = gf_odf_delete_descriptor_list(iod->ES_ID_IncDescriptors);
768 if (e) return e;
769 e = gf_odf_delete_descriptor_list(iod->ES_ID_RefDescriptors);
770 if (e) return e;
771 e = gf_odf_delete_descriptor_list(iod->OCIDescriptors);
772 if (e) return e;
773 e = gf_odf_delete_descriptor_list(iod->IPMP_Descriptors);
774 if (e) return e;
775 e = gf_odf_delete_descriptor_list(iod->extensionDescriptors);
776 if (e) return e;
777 if (iod->IPMPToolList) gf_odf_delete_descriptor((GF_Descriptor *)iod->IPMPToolList);
778 gf_free(iod);
779 return GF_OK;
780 }
781
AddDescriptorToIsomIOD(GF_IsomInitialObjectDescriptor * iod,GF_Descriptor * desc)782 GF_Err AddDescriptorToIsomIOD(GF_IsomInitialObjectDescriptor *iod, GF_Descriptor *desc)
783 {
784 if (!iod || !desc) return GF_BAD_PARAM;
785
786 switch (desc->tag) {
787 case GF_ODF_ESD_TAG:
788 return GF_ODF_FORBIDDEN_DESCRIPTOR;
789
790 case GF_ODF_ESD_INC_TAG:
791 //there shouldn't be ref if inc
792 if (gf_list_count(iod->ES_ID_RefDescriptors)) return GF_ODF_FORBIDDEN_DESCRIPTOR;
793 return gf_list_add(iod->ES_ID_IncDescriptors, desc);
794
795 case GF_ODF_ESD_REF_TAG:
796 //there shouldn't be inc if ref
797 if (gf_list_count(iod->ES_ID_IncDescriptors)) return GF_ODF_FORBIDDEN_DESCRIPTOR;
798 return gf_list_add(iod->ES_ID_RefDescriptors, desc);
799
800 //we use the same struct for v1 and v2 IPMP DPs
801 case GF_ODF_IPMP_PTR_TAG:
802 case GF_ODF_IPMP_TAG:
803 return gf_list_add(iod->IPMP_Descriptors, desc);
804
805 /*IPMPX*/
806 case GF_ODF_IPMP_TL_TAG:
807 if (iod->IPMPToolList) gf_odf_desc_del((GF_Descriptor *)iod->IPMPToolList);
808 iod->IPMPToolList = (GF_IPMP_ToolList *)desc;
809 return GF_OK;
810
811 default:
812 break;
813 }
814 //check if we can handle ContentClassif tags
815 if ((desc->tag >= GF_ODF_OCI_BEGIN_TAG) && (desc->tag <= GF_ODF_OCI_END_TAG)) return gf_list_add(iod->OCIDescriptors, desc);
816 //or extensions
817 if ((desc->tag >= GF_ODF_EXT_BEGIN_TAG) && (desc->tag <= GF_ODF_EXT_END_TAG)) return gf_list_add(iod->extensionDescriptors, desc);
818 return GF_BAD_PARAM;
819 }
820
gf_odf_read_isom_iod(GF_BitStream * bs,GF_IsomInitialObjectDescriptor * iod,u32 DescSize)821 GF_Err gf_odf_read_isom_iod(GF_BitStream *bs, GF_IsomInitialObjectDescriptor *iod, u32 DescSize)
822 {
823 u32 nbBytes = 0, tmpSize;
824 u32 urlflag;
825 GF_Err e;
826 if (!iod) return GF_BAD_PARAM;
827
828 iod->objectDescriptorID = gf_bs_read_int(bs, 10);
829 urlflag = gf_bs_read_int(bs, 1);
830 iod->inlineProfileFlag = gf_bs_read_int(bs, 1);
831 /*reserved = */gf_bs_read_int(bs, 4);
832 nbBytes += 2;
833
834 if (urlflag) {
835 u32 read;
836 e = gf_odf_read_url_string(bs, &iod->URLString, &read);
837 if (e) return e;
838 nbBytes += read;
839 }
840 else {
841 iod->OD_profileAndLevel = gf_bs_read_int(bs, 8);
842 iod->scene_profileAndLevel = gf_bs_read_int(bs, 8);
843 iod->audio_profileAndLevel = gf_bs_read_int(bs, 8);
844 iod->visual_profileAndLevel = gf_bs_read_int(bs, 8);
845 iod->graphics_profileAndLevel = gf_bs_read_int(bs, 8);
846 nbBytes += 5;
847 }
848
849 while (nbBytes < DescSize) {
850 GF_Descriptor *tmp = NULL;
851 e = gf_odf_parse_descriptor(bs, &tmp, &tmpSize);
852 if (e) return e;
853 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
854 e = AddDescriptorToIsomIOD(iod, tmp);
855 if (e) return e;
856 nbBytes += tmpSize + gf_odf_size_field_size(tmpSize);
857 }
858 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
859 return GF_OK;
860 }
861
gf_odf_size_isom_iod(GF_IsomInitialObjectDescriptor * iod,u32 * outSize)862 GF_Err gf_odf_size_isom_iod(GF_IsomInitialObjectDescriptor *iod, u32 *outSize)
863 {
864 GF_Err e;
865 if (!iod) return GF_BAD_PARAM;
866
867 *outSize = 2;
868 if (iod->URLString) {
869 *outSize += gf_odf_size_url_string(iod->URLString);
870 }
871 else {
872 *outSize += 5;
873 e = gf_odf_size_descriptor_list(iod->ES_ID_IncDescriptors, outSize);
874 if (e) return e;
875 e = gf_odf_size_descriptor_list(iod->ES_ID_RefDescriptors, outSize);
876 if (e) return e;
877 e = gf_odf_size_descriptor_list(iod->OCIDescriptors, outSize);
878 if (e) return e;
879 e = gf_odf_size_descriptor_list(iod->IPMP_Descriptors, outSize);
880 if (e) return e;
881 }
882 if (iod->IPMPToolList) {
883 u32 tmpSize;
884 e = gf_odf_size_descriptor((GF_Descriptor *)iod->IPMPToolList, &tmpSize);
885 if (e) return e;
886 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
887 }
888 return gf_odf_size_descriptor_list(iod->extensionDescriptors, outSize);
889 }
890
gf_odf_write_isom_iod(GF_BitStream * bs,GF_IsomInitialObjectDescriptor * iod)891 GF_Err gf_odf_write_isom_iod(GF_BitStream *bs, GF_IsomInitialObjectDescriptor *iod)
892 {
893 GF_Err e;
894 u32 size;
895 if (!iod) return GF_BAD_PARAM;
896
897 e = gf_odf_size_descriptor((GF_Descriptor *)iod, &size);
898 if (e) return e;
899 e = gf_odf_write_base_descriptor(bs, iod->tag, size);
900 if (e) return e;
901
902 gf_bs_write_int(bs, iod->objectDescriptorID, 10);
903 gf_bs_write_int(bs, iod->URLString != NULL ? 1 : 0, 1);
904 gf_bs_write_int(bs, iod->inlineProfileFlag, 1);
905 gf_bs_write_int(bs, 15, 4); //reserved: 0b1111 == 15
906
907 if (iod->URLString) {
908 gf_odf_write_url_string(bs, iod->URLString);
909 }
910 else {
911 gf_bs_write_int(bs, iod->OD_profileAndLevel, 8);
912 gf_bs_write_int(bs, iod->scene_profileAndLevel, 8);
913 gf_bs_write_int(bs, iod->audio_profileAndLevel, 8);
914 gf_bs_write_int(bs, iod->visual_profileAndLevel, 8);
915 gf_bs_write_int(bs, iod->graphics_profileAndLevel, 8);
916 e = gf_odf_write_descriptor_list(bs, iod->ES_ID_IncDescriptors);
917 if (e) return e;
918 e = gf_odf_write_descriptor_list(bs, iod->ES_ID_RefDescriptors);
919 if (e) return e;
920 e = gf_odf_write_descriptor_list(bs, iod->OCIDescriptors);
921 if (e) return e;
922 e = gf_odf_write_descriptor_list_filter(bs, iod->IPMP_Descriptors, GF_ODF_IPMP_PTR_TAG);
923 if (e) return e;
924 e = gf_odf_write_descriptor_list_filter(bs, iod->IPMP_Descriptors, GF_ODF_IPMP_TAG);
925 if (e) return e;
926 if (iod->IPMPToolList) {
927 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)iod->IPMPToolList);
928 if (e) return e;
929 }
930 }
931 e = gf_odf_write_descriptor_list(bs, iod->extensionDescriptors);
932 if (e) return e;
933 return GF_OK;
934 }
935
936
gf_odf_new_isom_od()937 GF_Descriptor *gf_odf_new_isom_od()
938 {
939 GF_IsomObjectDescriptor *newDesc = (GF_IsomObjectDescriptor *)gf_malloc(sizeof(GF_IsomObjectDescriptor));
940 if (!newDesc) return NULL;
941
942 newDesc->URLString = NULL;
943 newDesc->ES_ID_IncDescriptors = gf_list_new();
944 newDesc->ES_ID_RefDescriptors = gf_list_new();
945 newDesc->OCIDescriptors = gf_list_new();
946 newDesc->IPMP_Descriptors = gf_list_new();
947 newDesc->extensionDescriptors = gf_list_new();
948 newDesc->objectDescriptorID = 0;
949 newDesc->tag = GF_ODF_ISOM_OD_TAG;
950 return (GF_Descriptor *)newDesc;
951 }
952
gf_odf_del_isom_od(GF_IsomObjectDescriptor * od)953 GF_Err gf_odf_del_isom_od(GF_IsomObjectDescriptor *od)
954 {
955 GF_Err e;
956 if (!od) return GF_BAD_PARAM;
957 if (od->URLString) gf_free(od->URLString);
958 e = gf_odf_delete_descriptor_list(od->ES_ID_IncDescriptors);
959 if (e) return e;
960 e = gf_odf_delete_descriptor_list(od->ES_ID_RefDescriptors);
961 if (e) return e;
962 e = gf_odf_delete_descriptor_list(od->OCIDescriptors);
963 if (e) return e;
964 e = gf_odf_delete_descriptor_list(od->IPMP_Descriptors);
965 if (e) return e;
966 e = gf_odf_delete_descriptor_list(od->extensionDescriptors);
967 if (e) return e;
968 gf_free(od);
969 return GF_OK;
970 }
971
AddDescriptorToIsomOD(GF_IsomObjectDescriptor * od,GF_Descriptor * desc)972 GF_Err AddDescriptorToIsomOD(GF_IsomObjectDescriptor *od, GF_Descriptor *desc)
973 {
974 if (!od || !desc) return GF_BAD_PARAM;
975
976 //check if we can handle ContentClassif tags
977 if ((desc->tag >= GF_ODF_OCI_BEGIN_TAG) &&
978 (desc->tag <= GF_ODF_OCI_END_TAG)) {
979 return gf_list_add(od->OCIDescriptors, desc);
980 }
981
982 //or extension ...
983 if ((desc->tag >= GF_ODF_EXT_BEGIN_TAG) &&
984 (desc->tag <= GF_ODF_EXT_END_TAG)) {
985 return gf_list_add(od->extensionDescriptors, desc);
986 }
987
988 switch (desc->tag) {
989 case GF_ODF_ESD_TAG:
990 return GF_ODF_FORBIDDEN_DESCRIPTOR;
991
992 case GF_ODF_ESD_INC_TAG:
993 //there shouldn't be ref if inc
994 if (gf_list_count(od->ES_ID_RefDescriptors)) return GF_ODF_FORBIDDEN_DESCRIPTOR;
995 return gf_list_add(od->ES_ID_IncDescriptors, desc);
996
997 case GF_ODF_ESD_REF_TAG:
998 //there shouldn't be inc if ref
999 if (gf_list_count(od->ES_ID_IncDescriptors)) return GF_ODF_FORBIDDEN_DESCRIPTOR;
1000 return gf_list_add(od->ES_ID_RefDescriptors, desc);
1001
1002 //we use the same struct for v1 and v2 IPMP DPs
1003 case GF_ODF_IPMP_PTR_TAG:
1004 case GF_ODF_IPMP_TAG:
1005 return gf_list_add(od->IPMP_Descriptors, desc);
1006
1007 default:
1008 return GF_BAD_PARAM;
1009 }
1010 }
1011
gf_odf_read_isom_od(GF_BitStream * bs,GF_IsomObjectDescriptor * od,u32 DescSize)1012 GF_Err gf_odf_read_isom_od(GF_BitStream *bs, GF_IsomObjectDescriptor *od, u32 DescSize)
1013 {
1014 GF_Err e;
1015 u32 urlflag;
1016 u32 tmpSize, nbBytes = 0;
1017 if (!od) return GF_BAD_PARAM;
1018
1019 od->objectDescriptorID = gf_bs_read_int(bs, 10);
1020 urlflag = gf_bs_read_int(bs, 1);
1021 /*reserved = */gf_bs_read_int(bs, 5);
1022 nbBytes += 2;
1023
1024 if (urlflag) {
1025 u32 read;
1026 e = gf_odf_read_url_string(bs, &od->URLString, &read);
1027 if (e) return e;
1028 nbBytes += read;
1029 }
1030
1031 while (nbBytes < DescSize) {
1032 GF_Descriptor *tmp = NULL;
1033 e = gf_odf_parse_descriptor(bs, &tmp, &tmpSize);
1034 if (e) return e;
1035 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
1036 e = AddDescriptorToIsomOD(od, tmp);
1037 if (e) return e;
1038 nbBytes += tmpSize + gf_odf_size_field_size(tmpSize);
1039 }
1040 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
1041 return GF_OK;
1042 }
1043
gf_odf_size_isom_od(GF_IsomObjectDescriptor * od,u32 * outSize)1044 GF_Err gf_odf_size_isom_od(GF_IsomObjectDescriptor *od, u32 *outSize)
1045 {
1046 GF_Err e;
1047 if (!od) return GF_BAD_PARAM;
1048
1049 *outSize = 2;
1050 if (od->URLString) {
1051 *outSize += gf_odf_size_url_string(od->URLString);
1052 }
1053 else {
1054 e = gf_odf_size_descriptor_list(od->ES_ID_IncDescriptors, outSize);
1055 if (e) return e;
1056 e = gf_odf_size_descriptor_list(od->ES_ID_RefDescriptors, outSize);
1057 if (e) return e;
1058 e = gf_odf_size_descriptor_list(od->OCIDescriptors, outSize);
1059 if (e) return e;
1060 e = gf_odf_size_descriptor_list(od->IPMP_Descriptors, outSize);
1061 if (e) return e;
1062 }
1063 return gf_odf_size_descriptor_list(od->extensionDescriptors, outSize);
1064 }
1065
gf_odf_write_isom_od(GF_BitStream * bs,GF_IsomObjectDescriptor * od)1066 GF_Err gf_odf_write_isom_od(GF_BitStream *bs, GF_IsomObjectDescriptor *od)
1067 {
1068 GF_Err e;
1069 u32 size;
1070 if (!od) return GF_BAD_PARAM;
1071
1072 e = gf_odf_size_descriptor((GF_Descriptor *)od, &size);
1073 if (e) return e;
1074 e = gf_odf_write_base_descriptor(bs, od->tag, size);
1075 if (e) return e;
1076
1077 gf_bs_write_int(bs, od->objectDescriptorID, 10);
1078 gf_bs_write_int(bs, od->URLString != NULL ? 1 : 0, 1);
1079 gf_bs_write_int(bs, 31, 5); //reserved: 0b1111.1 == 31
1080
1081 if (od->URLString) {
1082 gf_odf_write_url_string(bs, od->URLString);
1083 }
1084 else {
1085 e = gf_odf_write_descriptor_list(bs, od->ES_ID_IncDescriptors);
1086 if (e) return e;
1087 e = gf_odf_write_descriptor_list(bs, od->ES_ID_RefDescriptors);
1088 if (e) return e;
1089 e = gf_odf_write_descriptor_list(bs, od->OCIDescriptors);
1090 if (e) return e;
1091 e = gf_odf_write_descriptor_list_filter(bs, od->IPMP_Descriptors, GF_ODF_IPMP_PTR_TAG);
1092 if (e) return e;
1093 e = gf_odf_write_descriptor_list_filter(bs, od->IPMP_Descriptors, GF_ODF_IPMP_TAG);
1094 if (e) return e;
1095 }
1096 e = gf_odf_write_descriptor_list(bs, od->extensionDescriptors);
1097 if (e) return e;
1098 return GF_OK;
1099 }
1100
1101
1102
gf_odf_new_dcd()1103 GF_Descriptor *gf_odf_new_dcd()
1104 {
1105 GF_DecoderConfig *newDesc;
1106 GF_SAFEALLOC(newDesc, GF_DecoderConfig);
1107 if (!newDesc) return NULL;
1108
1109 newDesc->profileLevelIndicationIndexDescriptor = gf_list_new();
1110 newDesc->tag = GF_ODF_DCD_TAG;
1111 return (GF_Descriptor *)newDesc;
1112 }
1113
gf_odf_del_dcd(GF_DecoderConfig * dcd)1114 GF_Err gf_odf_del_dcd(GF_DecoderConfig *dcd)
1115 {
1116 GF_Err e;
1117 if (!dcd) return GF_BAD_PARAM;
1118
1119 if (dcd->decoderSpecificInfo) {
1120 e = gf_odf_delete_descriptor((GF_Descriptor *)dcd->decoderSpecificInfo);
1121 if (e) return e;
1122 }
1123 if (dcd->rvc_config) {
1124 e = gf_odf_delete_descriptor((GF_Descriptor *)dcd->rvc_config);
1125 if (e) return e;
1126 }
1127 e = gf_odf_delete_descriptor_list(dcd->profileLevelIndicationIndexDescriptor);
1128 if (e) return e;
1129 gf_free(dcd);
1130 return GF_OK;
1131 }
1132
gf_odf_read_dcd(GF_BitStream * bs,GF_DecoderConfig * dcd,u32 DescSize)1133 GF_Err gf_odf_read_dcd(GF_BitStream *bs, GF_DecoderConfig *dcd, u32 DescSize)
1134 {
1135 GF_Err e;
1136 u32 /*reserved, */tmp_size, nbBytes = 0;
1137 if (!dcd) return GF_BAD_PARAM;
1138
1139 dcd->objectTypeIndication = gf_bs_read_int(bs, 8);
1140 dcd->streamType = gf_bs_read_int(bs, 6);
1141 dcd->upstream = gf_bs_read_int(bs, 1);
1142 /*reserved = */gf_bs_read_int(bs, 1);
1143 dcd->bufferSizeDB = gf_bs_read_int(bs, 24);
1144 dcd->maxBitrate = gf_bs_read_int(bs, 32);
1145 dcd->avgBitrate = gf_bs_read_int(bs, 32);
1146 nbBytes += 13;
1147
1148 while (nbBytes < DescSize) {
1149 GF_Descriptor *tmp = NULL;
1150 e = gf_odf_parse_descriptor(bs, &tmp, &tmp_size);
1151 if (e) return e;
1152 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
1153 switch (tmp->tag) {
1154 case GF_ODF_DSI_TAG:
1155 if (dcd->decoderSpecificInfo) {
1156 gf_odf_delete_descriptor(tmp);
1157 return GF_ODF_INVALID_DESCRIPTOR;
1158 }
1159 dcd->decoderSpecificInfo = (GF_DefaultDescriptor *)tmp;
1160 break;
1161
1162 case GF_ODF_EXT_PL_TAG:
1163 e = gf_list_add(dcd->profileLevelIndicationIndexDescriptor, tmp);
1164 if (e < GF_OK) {
1165 gf_odf_delete_descriptor(tmp);
1166 return e;
1167 }
1168 break;
1169
1170 /*iPod fix: delete and aborts, this will create an InvalidDescriptor at the ESD level with a loaded DSI,
1171 loading will abort with a partially valid ESD which is all the matters*/
1172 case GF_ODF_SLC_TAG:
1173 gf_odf_delete_descriptor(tmp);
1174 return GF_OK;
1175
1176 //what the hell is this descriptor ?? Don't know, so delete it !
1177 default:
1178 gf_odf_delete_descriptor(tmp);
1179 break;
1180 }
1181 nbBytes += tmp_size + gf_odf_size_field_size(tmp_size);
1182 }
1183 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
1184 return GF_OK;
1185 }
1186
gf_odf_size_dcd(GF_DecoderConfig * dcd,u32 * outSize)1187 GF_Err gf_odf_size_dcd(GF_DecoderConfig *dcd, u32 *outSize)
1188 {
1189 GF_Err e;
1190 u32 tmpSize;
1191 if (!dcd) return GF_BAD_PARAM;
1192
1193 *outSize = 0;
1194 *outSize += 13;
1195 if (dcd->decoderSpecificInfo) {
1196 //warning: we don't know anything about the structure of a generic DecSpecInfo
1197 //we check the tag and size of the descriptor, but we most ofthe time can't parse it
1198 //the decSpecInfo is handle as a defaultDescriptor (opaque data, but same structure....)
1199 e = gf_odf_size_descriptor((GF_Descriptor *)dcd->decoderSpecificInfo, &tmpSize);
1200 if (e) return e;
1201 *outSize += tmpSize + gf_odf_size_field_size(tmpSize);
1202 }
1203 e = gf_odf_size_descriptor_list(dcd->profileLevelIndicationIndexDescriptor, outSize);
1204 if (e) return e;
1205 return GF_OK;
1206 }
1207
gf_odf_write_dcd(GF_BitStream * bs,GF_DecoderConfig * dcd)1208 GF_Err gf_odf_write_dcd(GF_BitStream *bs, GF_DecoderConfig *dcd)
1209 {
1210 GF_Err e;
1211 u32 size;
1212 if (!dcd) return GF_BAD_PARAM;
1213
1214 e = gf_odf_size_descriptor((GF_Descriptor *)dcd, &size);
1215 if (e) return e;
1216 e = gf_odf_write_base_descriptor(bs, dcd->tag, size);
1217 if (e) return e;
1218
1219 gf_bs_write_int(bs, dcd->objectTypeIndication, 8);
1220 gf_bs_write_int(bs, dcd->streamType, 6);
1221 gf_bs_write_int(bs, dcd->upstream, 1);
1222 gf_bs_write_int(bs, 1, 1); //reserved field...
1223 gf_bs_write_int(bs, dcd->bufferSizeDB, 24);
1224 gf_bs_write_int(bs, dcd->maxBitrate, 32);
1225 gf_bs_write_int(bs, dcd->avgBitrate, 32);
1226
1227 if (dcd->decoderSpecificInfo) {
1228 e = gf_odf_write_descriptor(bs, (GF_Descriptor *)dcd->decoderSpecificInfo);
1229 if (e) return e;
1230 }
1231 e = gf_odf_write_descriptor_list(bs, dcd->profileLevelIndicationIndexDescriptor);
1232 return e;
1233 }
1234
1235
gf_odf_new_default()1236 GF_Descriptor *gf_odf_new_default()
1237 {
1238 GF_DefaultDescriptor *newDesc = (GF_DefaultDescriptor *)gf_malloc(sizeof(GF_DefaultDescriptor));
1239 if (!newDesc) return NULL;
1240
1241 newDesc->dataLength = 0;
1242 newDesc->data = NULL;
1243 //set it to the Max allowed
1244 newDesc->tag = GF_ODF_USER_END_TAG;
1245 return (GF_Descriptor *)newDesc;
1246 }
1247
gf_odf_del_default(GF_DefaultDescriptor * dd)1248 GF_Err gf_odf_del_default(GF_DefaultDescriptor *dd)
1249 {
1250 if (!dd) return GF_BAD_PARAM;
1251
1252 if (dd->data) gf_free(dd->data);
1253 gf_free(dd);
1254 return GF_OK;
1255 }
1256
gf_odf_read_default(GF_BitStream * bs,GF_DefaultDescriptor * dd,u32 DescSize)1257 GF_Err gf_odf_read_default(GF_BitStream *bs, GF_DefaultDescriptor *dd, u32 DescSize)
1258 {
1259 u32 nbBytes = 0;
1260 if (!dd) return GF_BAD_PARAM;
1261
1262 dd->dataLength = DescSize;
1263 dd->data = NULL;
1264 if (DescSize) {
1265 dd->data = (char*)gf_malloc(dd->dataLength);
1266 if (!dd->data) return GF_OUT_OF_MEM;
1267 gf_bs_read_data(bs, dd->data, dd->dataLength);
1268 nbBytes += dd->dataLength;
1269 }
1270 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
1271 return GF_OK;
1272 }
1273
gf_odf_size_default(GF_DefaultDescriptor * dd,u32 * outSize)1274 GF_Err gf_odf_size_default(GF_DefaultDescriptor *dd, u32 *outSize)
1275 {
1276 if (!dd) return GF_BAD_PARAM;
1277 *outSize = dd->dataLength;
1278 return GF_OK;
1279 }
1280
gf_odf_write_default(GF_BitStream * bs,GF_DefaultDescriptor * dd)1281 GF_Err gf_odf_write_default(GF_BitStream *bs, GF_DefaultDescriptor *dd)
1282 {
1283 GF_Err e;
1284 u32 size;
1285 if (!dd) return GF_BAD_PARAM;
1286
1287 e = gf_odf_size_descriptor((GF_Descriptor *)dd, &size);
1288 if (e) return e;
1289 e = gf_odf_write_base_descriptor(bs, dd->tag, size);
1290 if (e) return e;
1291
1292 if (dd->data) {
1293 gf_bs_write_data(bs, dd->data, dd->dataLength);
1294 }
1295 return GF_OK;
1296 }
1297
gf_odf_new_esd_inc()1298 GF_Descriptor *gf_odf_new_esd_inc()
1299 {
1300 GF_ES_ID_Inc *newDesc = (GF_ES_ID_Inc *)gf_malloc(sizeof(GF_ES_ID_Inc));
1301 if (!newDesc) return NULL;
1302 newDesc->tag = GF_ODF_ESD_INC_TAG;
1303 newDesc->trackID = 0;
1304 return (GF_Descriptor *)newDesc;
1305 }
1306
gf_odf_del_esd_inc(GF_ES_ID_Inc * esd_inc)1307 GF_Err gf_odf_del_esd_inc(GF_ES_ID_Inc *esd_inc)
1308 {
1309 if (!esd_inc) return GF_BAD_PARAM;
1310 gf_free(esd_inc);
1311 return GF_OK;
1312 }
gf_odf_read_esd_inc(GF_BitStream * bs,GF_ES_ID_Inc * esd_inc,u32 DescSize)1313 GF_Err gf_odf_read_esd_inc(GF_BitStream *bs, GF_ES_ID_Inc *esd_inc, u32 DescSize)
1314 {
1315 u32 nbBytes = 0;
1316 if (!esd_inc) return GF_BAD_PARAM;
1317
1318 esd_inc->trackID = gf_bs_read_int(bs, 32);
1319 nbBytes += 4;
1320 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
1321 return GF_OK;
1322 }
gf_odf_size_esd_inc(GF_ES_ID_Inc * esd_inc,u32 * outSize)1323 GF_Err gf_odf_size_esd_inc(GF_ES_ID_Inc *esd_inc, u32 *outSize)
1324 {
1325 if (!esd_inc) return GF_BAD_PARAM;
1326 *outSize = 4;
1327 return GF_OK;
1328 }
gf_odf_write_esd_inc(GF_BitStream * bs,GF_ES_ID_Inc * esd_inc)1329 GF_Err gf_odf_write_esd_inc(GF_BitStream *bs, GF_ES_ID_Inc *esd_inc)
1330 {
1331 GF_Err e;
1332 u32 size;
1333 if (!esd_inc) return GF_BAD_PARAM;
1334
1335 e = gf_odf_size_descriptor((GF_Descriptor *)esd_inc, &size);
1336 if (e) return e;
1337 e = gf_odf_write_base_descriptor(bs, esd_inc->tag, size);
1338 if (e) return e;
1339 gf_bs_write_int(bs, esd_inc->trackID, 32);
1340 return GF_OK;
1341 }
1342
gf_odf_new_esd_ref()1343 GF_Descriptor *gf_odf_new_esd_ref()
1344 {
1345 GF_ES_ID_Ref *newDesc = (GF_ES_ID_Ref *)gf_malloc(sizeof(GF_ES_ID_Ref));
1346 if (!newDesc) return NULL;
1347 newDesc->tag = GF_ODF_ESD_REF_TAG;
1348 newDesc->trackRef = 0;
1349 return (GF_Descriptor *)newDesc;
1350 }
1351
gf_odf_del_esd_ref(GF_ES_ID_Ref * esd_ref)1352 GF_Err gf_odf_del_esd_ref(GF_ES_ID_Ref *esd_ref)
1353 {
1354 if (!esd_ref) return GF_BAD_PARAM;
1355 gf_free(esd_ref);
1356 return GF_OK;
1357 }
gf_odf_read_esd_ref(GF_BitStream * bs,GF_ES_ID_Ref * esd_ref,u32 DescSize)1358 GF_Err gf_odf_read_esd_ref(GF_BitStream *bs, GF_ES_ID_Ref *esd_ref, u32 DescSize)
1359 {
1360 u32 nbBytes = 0;
1361 if (!esd_ref) return GF_BAD_PARAM;
1362
1363 esd_ref->trackRef = gf_bs_read_int(bs, 16);
1364 nbBytes += 2;
1365 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
1366 return GF_OK;
1367 }
1368
gf_odf_size_esd_ref(GF_ES_ID_Ref * esd_ref,u32 * outSize)1369 GF_Err gf_odf_size_esd_ref(GF_ES_ID_Ref *esd_ref, u32 *outSize)
1370 {
1371 if (!esd_ref) return GF_BAD_PARAM;
1372 *outSize = 2;
1373 return GF_OK;
1374 }
gf_odf_write_esd_ref(GF_BitStream * bs,GF_ES_ID_Ref * esd_ref)1375 GF_Err gf_odf_write_esd_ref(GF_BitStream *bs, GF_ES_ID_Ref *esd_ref)
1376 {
1377 GF_Err e;
1378 u32 size;
1379 if (!esd_ref) return GF_BAD_PARAM;
1380
1381 e = gf_odf_size_descriptor((GF_Descriptor *)esd_ref, &size);
1382 if (e) return e;
1383 e = gf_odf_write_base_descriptor(bs, esd_ref->tag, size);
1384 if (e) return e;
1385
1386 gf_bs_write_int(bs, esd_ref->trackRef, 16);
1387 return GF_OK;
1388 }
1389
1390
1391
gf_odf_new_segment()1392 GF_Descriptor *gf_odf_new_segment()
1393 {
1394 GF_Segment *newDesc = (GF_Segment *)gf_malloc(sizeof(GF_Segment));
1395 if (!newDesc) return NULL;
1396
1397 memset(newDesc, 0, sizeof(GF_Segment));
1398 newDesc->tag = GF_ODF_SEGMENT_TAG;
1399 return (GF_Descriptor *)newDesc;
1400 }
1401
gf_odf_del_segment(GF_Segment * sd)1402 GF_Err gf_odf_del_segment(GF_Segment *sd)
1403 {
1404 if (!sd) return GF_BAD_PARAM;
1405
1406 if (sd->SegmentName) gf_free(sd->SegmentName);
1407 gf_free(sd);
1408 return GF_OK;
1409 }
1410
gf_odf_read_segment(GF_BitStream * bs,GF_Segment * sd,u32 DescSize)1411 GF_Err gf_odf_read_segment(GF_BitStream *bs, GF_Segment *sd, u32 DescSize)
1412 {
1413 u32 size, nbBytes = 0;
1414 if (!sd) return GF_BAD_PARAM;
1415
1416 sd->startTime = gf_bs_read_double(bs);
1417 sd->Duration = gf_bs_read_double(bs);
1418 nbBytes += 16;
1419 size = gf_bs_read_int(bs, 8);
1420 nbBytes += 1;
1421 if (size) {
1422 sd->SegmentName = (char*)gf_malloc(sizeof(char)*(size + 1));
1423 if (!sd->SegmentName) return GF_OUT_OF_MEM;
1424 gf_bs_read_data(bs, sd->SegmentName, size);
1425 sd->SegmentName[size] = 0;
1426 nbBytes += size;
1427 }
1428 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
1429 return GF_OK;
1430 }
1431
gf_odf_size_segment(GF_Segment * sd,u32 * outSize)1432 GF_Err gf_odf_size_segment(GF_Segment *sd, u32 *outSize)
1433 {
1434 if (!sd) return GF_BAD_PARAM;
1435 *outSize = 17;
1436 if (sd->SegmentName) *outSize += (u32)strlen(sd->SegmentName);
1437 return GF_OK;
1438 }
1439
gf_odf_write_segment(GF_BitStream * bs,GF_Segment * sd)1440 GF_Err gf_odf_write_segment(GF_BitStream *bs, GF_Segment *sd)
1441 {
1442 GF_Err e;
1443 u32 size;
1444 if (!sd) return GF_BAD_PARAM;
1445 e = gf_odf_size_descriptor((GF_Descriptor *)sd, &size);
1446 if (e) return e;
1447 e = gf_odf_write_base_descriptor(bs, sd->tag, size);
1448 if (e) return e;
1449 gf_bs_write_double(bs, sd->startTime);
1450 gf_bs_write_double(bs, sd->Duration);
1451 if (sd->SegmentName) {
1452 gf_bs_write_int(bs, (u32)strlen(sd->SegmentName), 8);
1453 gf_bs_write_data(bs, sd->SegmentName, (u32)strlen(sd->SegmentName));
1454 }
1455 else {
1456 gf_bs_write_int(bs, 0, 8);
1457 }
1458 return GF_OK;
1459 }
gf_odf_new_mediatime()1460 GF_Descriptor *gf_odf_new_mediatime()
1461 {
1462 GF_MediaTime *newDesc = (GF_MediaTime *)gf_malloc(sizeof(GF_MediaTime));
1463 if (!newDesc) return NULL;
1464
1465 memset(newDesc, 0, sizeof(GF_MediaTime));
1466 newDesc->tag = GF_ODF_MEDIATIME_TAG;
1467 return (GF_Descriptor *)newDesc;
1468 }
gf_odf_del_mediatime(GF_MediaTime * mt)1469 GF_Err gf_odf_del_mediatime(GF_MediaTime *mt)
1470 {
1471 if (!mt) return GF_BAD_PARAM;
1472 gf_free(mt);
1473 return GF_OK;
1474 }
gf_odf_read_mediatime(GF_BitStream * bs,GF_MediaTime * mt,u32 DescSize)1475 GF_Err gf_odf_read_mediatime(GF_BitStream *bs, GF_MediaTime *mt, u32 DescSize)
1476 {
1477 if (!mt) return GF_BAD_PARAM;
1478 mt->mediaTimeStamp = gf_bs_read_double(bs);
1479 return GF_OK;
1480 }
gf_odf_size_mediatime(GF_MediaTime * mt,u32 * outSize)1481 GF_Err gf_odf_size_mediatime(GF_MediaTime *mt, u32 *outSize)
1482 {
1483 if (!mt) return GF_BAD_PARAM;
1484 *outSize = 8;
1485 return GF_OK;
1486 }
gf_odf_write_mediatime(GF_BitStream * bs,GF_MediaTime * mt)1487 GF_Err gf_odf_write_mediatime(GF_BitStream *bs, GF_MediaTime *mt)
1488 {
1489 GF_Err e;
1490 u32 size;
1491 if (!mt) return GF_BAD_PARAM;
1492 e = gf_odf_size_descriptor((GF_Descriptor *)mt, &size);
1493 if (e) return e;
1494 e = gf_odf_write_base_descriptor(bs, mt->tag, size);
1495 if (e) return e;
1496 gf_bs_write_double(bs, mt->mediaTimeStamp);
1497 return GF_OK;
1498 }
1499
1500
gf_odf_new_lang()1501 GF_Descriptor *gf_odf_new_lang()
1502 {
1503 GF_Language *newDesc;
1504 GF_SAFEALLOC(newDesc, GF_Language);
1505 if (!newDesc) return NULL;
1506 newDesc->tag = GF_ODF_LANG_TAG;
1507 return (GF_Descriptor *)newDesc;
1508 }
1509
gf_odf_del_lang(GF_Language * ld)1510 GF_Err gf_odf_del_lang(GF_Language *ld)
1511 {
1512 if (!ld) return GF_BAD_PARAM;
1513 if (ld->full_lang_code) gf_free(ld->full_lang_code);
1514 gf_free(ld);
1515 return GF_OK;
1516 }
1517
gf_odf_read_lang(GF_BitStream * bs,GF_Language * ld,u32 DescSize)1518 GF_Err gf_odf_read_lang(GF_BitStream *bs, GF_Language *ld, u32 DescSize)
1519 {
1520 u32 nbBytes = 0;
1521 if (!ld) return GF_BAD_PARAM;
1522
1523 ld->langCode = gf_bs_read_int(bs, 24);
1524 nbBytes += 3;
1525 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
1526 return GF_OK;
1527 }
1528
gf_odf_size_lang(GF_Language * ld,u32 * outSize)1529 GF_Err gf_odf_size_lang(GF_Language *ld, u32 *outSize)
1530 {
1531 if (!ld) return GF_BAD_PARAM;
1532 *outSize = 3;
1533 return GF_OK;
1534 }
1535
gf_odf_write_lang(GF_BitStream * bs,GF_Language * ld)1536 GF_Err gf_odf_write_lang(GF_BitStream *bs, GF_Language *ld)
1537 {
1538 GF_Err e;
1539 u32 size;
1540 if (!ld) return GF_BAD_PARAM;
1541
1542 e = gf_odf_size_descriptor((GF_Descriptor *)ld, &size);
1543 if (e) return e;
1544 e = gf_odf_write_base_descriptor(bs, ld->tag, size);
1545 if (e) return e;
1546 gf_bs_write_int(bs, ld->langCode, 24);
1547 return GF_OK;
1548 }
1549
1550
1551
gf_odf_new_auxvid()1552 GF_Descriptor *gf_odf_new_auxvid()
1553 {
1554 GF_AuxVideoDescriptor *newDesc;
1555 GF_SAFEALLOC(newDesc, GF_AuxVideoDescriptor);
1556 if (!newDesc) return NULL;
1557 newDesc->tag = GF_ODF_AUX_VIDEO_DATA;
1558 return (GF_Descriptor *)newDesc;
1559 }
1560
gf_odf_del_auxvid(GF_AuxVideoDescriptor * ld)1561 GF_Err gf_odf_del_auxvid(GF_AuxVideoDescriptor *ld)
1562 {
1563 if (!ld) return GF_BAD_PARAM;
1564 gf_free(ld);
1565 return GF_OK;
1566 }
1567
gf_odf_read_auxvid(GF_BitStream * bs,GF_AuxVideoDescriptor * ld,u32 DescSize)1568 GF_Err gf_odf_read_auxvid(GF_BitStream *bs, GF_AuxVideoDescriptor *ld, u32 DescSize)
1569 {
1570 u32 nbBytes = 0;
1571 if (!ld) return GF_BAD_PARAM;
1572
1573 ld->aux_video_type = gf_bs_read_int(bs, 8);
1574 ld->position_offset_h = gf_bs_read_int(bs, 8);
1575 ld->position_offset_v = gf_bs_read_int(bs, 8);
1576 nbBytes += 3;
1577 switch (ld->aux_video_type) {
1578 case 0x10:
1579 ld->kfar = gf_bs_read_int(bs, 8);
1580 ld->knear = gf_bs_read_int(bs, 8);
1581 nbBytes += 2;
1582 break;
1583 case 0x11:
1584 ld->parallax_zero = gf_bs_read_int(bs, 16);
1585 ld->parallax_scale = gf_bs_read_int(bs, 16);
1586 ld->dref = gf_bs_read_int(bs, 16);
1587 ld->wref = gf_bs_read_int(bs, 16);
1588 nbBytes += 8;
1589 break;
1590 }
1591 while (nbBytes < DescSize) {
1592 gf_bs_read_int(bs, 8);
1593 nbBytes++;
1594 }
1595 return GF_OK;
1596 }
1597
gf_odf_size_auxvid(GF_AuxVideoDescriptor * ld,u32 * outSize)1598 GF_Err gf_odf_size_auxvid(GF_AuxVideoDescriptor *ld, u32 *outSize)
1599 {
1600 if (!ld) return GF_BAD_PARAM;
1601 switch (ld->aux_video_type) {
1602 case 0x10:
1603 *outSize = 5;
1604 break;
1605 case 0x11:
1606 *outSize = 11;
1607 break;
1608 default:
1609 *outSize = 3;
1610 break;
1611 }
1612 return GF_OK;
1613 }
1614
gf_odf_write_auxvid(GF_BitStream * bs,GF_AuxVideoDescriptor * ld)1615 GF_Err gf_odf_write_auxvid(GF_BitStream *bs, GF_AuxVideoDescriptor *ld)
1616 {
1617 GF_Err e;
1618 u32 size;
1619 if (!ld) return GF_BAD_PARAM;
1620 e = gf_odf_size_descriptor((GF_Descriptor *)ld, &size);
1621 if (e) return e;
1622 e = gf_odf_write_base_descriptor(bs, ld->tag, size);
1623 if (e) return e;
1624
1625 gf_bs_write_int(bs, ld->aux_video_type, 8);
1626 gf_bs_write_int(bs, ld->position_offset_h, 8);
1627 gf_bs_write_int(bs, ld->position_offset_v, 8);
1628 switch (ld->aux_video_type) {
1629 case 0x10:
1630 gf_bs_write_int(bs, ld->kfar, 8);
1631 gf_bs_write_int(bs, ld->knear, 8);
1632 break;
1633 case 0x11:
1634 gf_bs_write_int(bs, ld->parallax_zero, 16);
1635 gf_bs_write_int(bs, ld->parallax_scale, 16);
1636 gf_bs_write_int(bs, ld->dref, 16);
1637 gf_bs_write_int(bs, ld->wref, 16);
1638 break;
1639 }
1640 return GF_OK;
1641 }
1642
1643
1644
gf_odf_new_muxinfo()1645 GF_Descriptor *gf_odf_new_muxinfo()
1646 {
1647 GF_MuxInfo *newDesc = (GF_MuxInfo *)gf_malloc(sizeof(GF_MuxInfo));
1648 if (!newDesc) return NULL;
1649 memset(newDesc, 0, sizeof(GF_MuxInfo));
1650 newDesc->tag = GF_ODF_MUXINFO_TAG;
1651 return (GF_Descriptor *)newDesc;
1652 }
1653
gf_odf_del_muxinfo(GF_MuxInfo * mi)1654 GF_Err gf_odf_del_muxinfo(GF_MuxInfo *mi)
1655 {
1656 if (!mi) return GF_BAD_PARAM;
1657 if (mi->file_name) gf_free(mi->file_name);
1658 if (mi->src_url) gf_free(mi->src_url);
1659 if (mi->streamFormat) gf_free(mi->streamFormat);
1660 if (mi->textNode) gf_free(mi->textNode);
1661 if (mi->fontNode) gf_free(mi->fontNode);
1662 gf_free(mi);
1663 return GF_OK;
1664 }
1665
gf_odf_read_muxinfo(GF_BitStream * bs,GF_MuxInfo * mi,u32 DescSize)1666 GF_Err gf_odf_read_muxinfo(GF_BitStream *bs, GF_MuxInfo *mi, u32 DescSize)
1667 {
1668 return GF_OK;
1669 }
gf_odf_size_muxinfo(GF_MuxInfo * mi,u32 * outSize)1670 GF_Err gf_odf_size_muxinfo(GF_MuxInfo *mi, u32 *outSize)
1671 {
1672 *outSize = 0;
1673 return GF_OK;
1674 }
gf_odf_write_muxinfo(GF_BitStream * bs,GF_MuxInfo * mi)1675 GF_Err gf_odf_write_muxinfo(GF_BitStream *bs, GF_MuxInfo *mi)
1676 {
1677 return GF_OK;
1678 }
1679
gf_odf_New_ElemMask()1680 GF_Descriptor *gf_odf_New_ElemMask()
1681 {
1682 GF_ElementaryMask *newDesc = (GF_ElementaryMask*)gf_malloc(sizeof(GF_ElementaryMask));
1683 if (!newDesc) return NULL;
1684 memset(newDesc, 0, sizeof(GF_ElementaryMask));
1685 newDesc->tag = GF_ODF_ELEM_MASK_TAG;
1686 return (GF_Descriptor *)newDesc;
1687 }
1688
gf_odf_del_ElemMask(GF_ElementaryMask * desc)1689 GF_Err gf_odf_del_ElemMask(GF_ElementaryMask *desc)
1690 {
1691 if (desc->node_name) gf_free(desc->node_name);
1692 gf_free(desc);
1693 return GF_OK;
1694 }
1695
gf_odf_new_bifs_cfg()1696 GF_Descriptor *gf_odf_new_bifs_cfg()
1697 {
1698 GF_BIFSConfig *newDesc = (GF_BIFSConfig *)gf_malloc(sizeof(GF_BIFSConfig));
1699 if (!newDesc) return NULL;
1700 memset(newDesc, 0, sizeof(GF_BIFSConfig));
1701 newDesc->tag = GF_ODF_BIFS_CFG_TAG;
1702 return (GF_Descriptor *)newDesc;
1703 }
1704
gf_odf_del_bifs_cfg(GF_BIFSConfig * desc)1705 GF_Err gf_odf_del_bifs_cfg(GF_BIFSConfig *desc)
1706 {
1707 if (desc->elementaryMasks) {
1708 u32 i, count = gf_list_count(desc->elementaryMasks);
1709 for (i = 0; i<count; i++) {
1710 GF_ElementaryMask *tmp = (GF_ElementaryMask *)gf_list_get(desc->elementaryMasks, i);
1711 if (tmp->node_name) gf_free(tmp->node_name);
1712 gf_free(tmp);
1713 }
1714 gf_list_del(desc->elementaryMasks);
1715 }
1716 gf_free(desc);
1717 return GF_OK;
1718 }
1719
gf_odf_new_laser_cfg()1720 GF_Descriptor *gf_odf_new_laser_cfg()
1721 {
1722 GF_LASERConfig *newDesc = (GF_LASERConfig *)gf_malloc(sizeof(GF_LASERConfig));
1723 if (!newDesc) return NULL;
1724 memset(newDesc, 0, sizeof(GF_LASERConfig));
1725 newDesc->tag = GF_ODF_LASER_CFG_TAG;
1726 return (GF_Descriptor *)newDesc;
1727 }
1728
gf_odf_del_laser_cfg(GF_LASERConfig * desc)1729 GF_Err gf_odf_del_laser_cfg(GF_LASERConfig *desc)
1730 {
1731 gf_free(desc);
1732 return GF_OK;
1733 }
1734
gf_odf_new_ui_cfg()1735 GF_Descriptor *gf_odf_new_ui_cfg()
1736 {
1737 GF_UIConfig *newDesc = (GF_UIConfig *)gf_malloc(sizeof(GF_UIConfig));
1738 if (!newDesc) return NULL;
1739 memset(newDesc, 0, sizeof(GF_UIConfig));
1740 newDesc->tag = GF_ODF_UI_CFG_TAG;
1741 return (GF_Descriptor *)newDesc;
1742 }
1743
gf_odf_del_ui_cfg(GF_UIConfig * desc)1744 GF_Err gf_odf_del_ui_cfg(GF_UIConfig *desc)
1745 {
1746 if (desc->deviceName) gf_free(desc->deviceName);
1747 if (desc->ui_data) gf_free(desc->ui_data);
1748 gf_free(desc);
1749 return GF_OK;
1750 }
1751
1752 #ifndef GPAC_MINIMAL_ODF
1753
1754
1755
gf_odf_new_cc()1756 GF_Descriptor *gf_odf_new_cc()
1757 {
1758 GF_CCDescriptor *newDesc = (GF_CCDescriptor *)gf_malloc(sizeof(GF_CCDescriptor));
1759 if (!newDesc) return NULL;
1760
1761 newDesc->contentClassificationData = NULL;
1762 newDesc->dataLength = 0;
1763 newDesc->classificationEntity = 0;
1764 newDesc->classificationTable = 0;
1765 newDesc->tag = GF_ODF_CC_TAG;
1766 return (GF_Descriptor *)newDesc;
1767 }
1768
gf_odf_del_cc(GF_CCDescriptor * ccd)1769 GF_Err gf_odf_del_cc(GF_CCDescriptor *ccd)
1770 {
1771 if (!ccd) return GF_BAD_PARAM;
1772 if (ccd->contentClassificationData) gf_free(ccd->contentClassificationData);
1773 gf_free(ccd);
1774 return GF_OK;
1775 }
1776
gf_odf_read_cc(GF_BitStream * bs,GF_CCDescriptor * ccd,u32 DescSize)1777 GF_Err gf_odf_read_cc(GF_BitStream *bs, GF_CCDescriptor *ccd, u32 DescSize)
1778 {
1779 u32 nbBytes = 0;
1780 if (!ccd) return GF_BAD_PARAM;
1781
1782 ccd->classificationEntity = gf_bs_read_int(bs, 32);
1783 ccd->classificationTable = gf_bs_read_int(bs, 16);
1784 nbBytes += 6;
1785 ccd->dataLength = DescSize - 6;
1786 ccd->contentClassificationData = (char*)gf_malloc(sizeof(char) * ccd->dataLength);
1787 if (!ccd->contentClassificationData) return GF_OUT_OF_MEM;
1788 gf_bs_read_data(bs, ccd->contentClassificationData, ccd->dataLength);
1789 nbBytes += ccd->dataLength;
1790
1791 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
1792 return GF_OK;
1793 }
1794
gf_odf_size_cc(GF_CCDescriptor * ccd,u32 * outSize)1795 GF_Err gf_odf_size_cc(GF_CCDescriptor *ccd, u32 *outSize)
1796 {
1797 if (!ccd) return GF_BAD_PARAM;
1798 *outSize = 6 + ccd->dataLength;
1799 return GF_OK;
1800 }
1801
gf_odf_write_cc(GF_BitStream * bs,GF_CCDescriptor * ccd)1802 GF_Err gf_odf_write_cc(GF_BitStream *bs, GF_CCDescriptor *ccd)
1803 {
1804 u32 size;
1805 GF_Err e;
1806 if (!ccd) return GF_BAD_PARAM;
1807
1808 e = gf_odf_size_descriptor((GF_Descriptor *)ccd, &size);
1809 if (e) return e;
1810 e = gf_odf_write_base_descriptor(bs, ccd->tag, size);
1811 if (e) return e;
1812 gf_bs_write_int(bs, ccd->classificationEntity, 32);
1813 gf_bs_write_int(bs, ccd->classificationTable, 16);
1814 gf_bs_write_data(bs, ccd->contentClassificationData, ccd->dataLength);
1815 return GF_OK;
1816 }
1817
gf_odf_new_cc_date()1818 GF_Descriptor *gf_odf_new_cc_date()
1819 {
1820 GF_CC_Date *newDesc = (GF_CC_Date *)gf_malloc(sizeof(GF_CC_Date));
1821 if (!newDesc) return NULL;
1822 memset(newDesc->contentCreationDate, 0, 5);
1823 newDesc->tag = GF_ODF_CC_DATE_TAG;
1824 return (GF_Descriptor *)newDesc;
1825 }
1826
1827
gf_odf_del_cc_date(GF_CC_Date * cdd)1828 GF_Err gf_odf_del_cc_date(GF_CC_Date *cdd)
1829 {
1830 if (!cdd) return GF_BAD_PARAM;
1831 gf_free(cdd);
1832 return GF_OK;
1833 }
1834
gf_odf_read_cc_date(GF_BitStream * bs,GF_CC_Date * cdd,u32 DescSize)1835 GF_Err gf_odf_read_cc_date(GF_BitStream *bs, GF_CC_Date *cdd, u32 DescSize)
1836 {
1837 u32 nbBytes = 0;
1838 if (!cdd) return GF_BAD_PARAM;
1839
1840 gf_bs_read_data(bs, cdd->contentCreationDate, DATE_CODING_BIT_LEN);
1841 nbBytes += DATE_CODING_BIT_LEN / 8;
1842 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
1843 return GF_OK;
1844 }
1845
gf_odf_size_cc_date(GF_CC_Date * cdd,u32 * outSize)1846 GF_Err gf_odf_size_cc_date(GF_CC_Date *cdd, u32 *outSize)
1847 {
1848 if (!cdd) return GF_BAD_PARAM;
1849 *outSize = (DATE_CODING_BIT_LEN / 8);
1850 return GF_OK;
1851 }
1852
gf_odf_write_cc_date(GF_BitStream * bs,GF_CC_Date * cdd)1853 GF_Err gf_odf_write_cc_date(GF_BitStream *bs, GF_CC_Date *cdd)
1854 {
1855 u32 size;
1856 GF_Err e;
1857 if (!cdd) return GF_BAD_PARAM;
1858
1859 e = gf_odf_size_descriptor((GF_Descriptor *)cdd, &size);
1860 if (e) return e;
1861 e = gf_odf_write_base_descriptor(bs, cdd->tag, size);
1862 if (e) return e;
1863
1864 gf_bs_write_data(bs, cdd->contentCreationDate, DATE_CODING_BIT_LEN);
1865 return GF_OK;
1866 }
1867
gf_odf_new_cc_name()1868 GF_Descriptor *gf_odf_new_cc_name()
1869 {
1870 GF_CC_Name *newDesc = (GF_CC_Name *)gf_malloc(sizeof(GF_CC_Name));
1871 if (!newDesc) return NULL;
1872
1873 newDesc->ContentCreators = gf_list_new();
1874 if (!newDesc->ContentCreators) {
1875 gf_free(newDesc);
1876 return NULL;
1877 }
1878 newDesc->tag = GF_ODF_CC_NAME_TAG;
1879 return (GF_Descriptor *)newDesc;
1880 }
1881
gf_odf_del_cc_name(GF_CC_Name * cnd)1882 GF_Err gf_odf_del_cc_name(GF_CC_Name *cnd)
1883 {
1884 u32 i;
1885 GF_ContentCreatorInfo *tmp;
1886 if (!cnd) return GF_BAD_PARAM;
1887
1888 i = 0;
1889 while ((tmp = (GF_ContentCreatorInfo *)gf_list_enum(cnd->ContentCreators, &i))) {
1890 if (tmp->contentCreatorName) gf_free(tmp->contentCreatorName);
1891 gf_free(tmp);
1892 }
1893 gf_list_del(cnd->ContentCreators);
1894 gf_free(cnd);
1895 return GF_OK;
1896 }
1897
gf_odf_read_cc_name(GF_BitStream * bs,GF_CC_Name * cnd,u32 DescSize)1898 GF_Err gf_odf_read_cc_name(GF_BitStream *bs, GF_CC_Name *cnd, u32 DescSize)
1899 {
1900 GF_Err e;
1901 u32 i, count, len, nbBytes = 0;
1902 if (!cnd) return GF_BAD_PARAM;
1903
1904 count = gf_bs_read_int(bs, 8);
1905 nbBytes += 1;
1906 for (i = 0; i< count; i++) {
1907 GF_ContentCreatorInfo *tmp = (GF_ContentCreatorInfo*)gf_malloc(sizeof(GF_ContentCreatorInfo));
1908 if (!tmp) return GF_OUT_OF_MEM;
1909 memset(tmp, 0, sizeof(GF_ContentCreatorInfo));
1910 tmp->langCode = gf_bs_read_int(bs, 24);
1911 tmp->isUTF8 = gf_bs_read_int(bs, 1);
1912 /*aligned = */gf_bs_read_int(bs, 7);
1913 nbBytes += 4;
1914
1915 e = OD_ReadUTF8String(bs, &tmp->contentCreatorName, tmp->isUTF8, &len);
1916 if (e) return e;
1917 nbBytes += len;
1918 e = gf_list_add(cnd->ContentCreators, tmp);
1919 if (e) return e;
1920 }
1921 if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;
1922 return GF_OK;
1923 }
1924
gf_odf_size_cc_name(GF_CC_Name * cnd,u32 * outSize)1925 GF_Err gf_odf_size_cc_name(GF_CC_Name *cnd, u32 *outSize)
1926 {
1927 u32 i;
1928 GF_ContentCreatorInfo *tmp;
1929 if (!cnd) return GF_BAD_PARAM;
1930
1931 *outSize = 1;
1932 i = 0;
1933 while ((tmp = (GF_ContentCreatorInfo *)gf_list_enum(cnd->ContentCreators, &i))) {
1934 *outSize += 4 + OD_SizeUTF8String(tmp->contentCreatorName, tmp->isUTF8);
1935 }
1936 return GF_OK;
1937 }
1938
gf_odf_write_cc_name(GF_BitStream * bs,GF_CC_Name * cnd)1939 GF_Err gf_odf_write_cc_name(GF_BitStream *bs, GF_CC_Name *cnd)
1940 {
1941 GF_Err e;
1942 GF_ContentCreatorInfo *tmp;
1943 u32 i, size;
1944 if (!cnd) return GF_BAD_PARAM;
1945
1946 e = gf_odf_size_descriptor((GF_Descriptor *)cnd, &size);
1947 if (e) return e;
1948 e = gf_odf_write_base_descriptor(bs, cnd->tag, size);
1949 if (e) return e;
1950 gf_bs_write_int(bs, gf_list_count(cnd->ContentCreators), 8);
1951
1952 i = 0;
1953 while ((tmp = (GF_ContentCreatorInfo *)gf_list_enum(cnd->ContentCreators, &i))) {
1954 gf_bs_write_int(bs, tmp->langCode, 24);
1955 gf_bs_write_int(bs, tmp->isUTF8, 1);
1956 gf_bs_write_int(bs, 0, 7); //aligned
1957 OD_WriteUTF8String(bs, tmp->contentCreatorName, tmp->isUTF8);
1958 }
1959 return GF_OK;
1960 }
1961
1962
gf_odf_new_ci()1963 GF_Descriptor *gf_odf_new_ci()
1964 {
1965 GF_CIDesc *newDesc = (GF_CIDesc *)gf_malloc(sizeof(GF_CIDesc));
1966 if (!newDesc) return NULL;
1967
1968 newDesc->compatibility = 0;
1969 newDesc->contentIdentifier = NULL;
1970 newDesc->tag = GF_ODF_CI_TAG;
1971 newDesc->contentIdentifierFlag = 0;
1972 newDesc->contentIdentifierType = 0;
1973 newDesc->contentType = 0;
1974 newDesc->contentTypeFlag = 0;
1975 newDesc->protectedContent = 0;
1976 return (GF_Descriptor *)newDesc;
1977 }
1978
1979
gf_odf_del_ci(GF_CIDesc * cid)1980 GF_Err gf_odf_del_ci(GF_CIDesc *cid)
1981 {
1982 if (!cid) return GF_BAD_PARAM;
1983
1984 if (cid->contentIdentifier) gf_free(cid->contentIdentifier);
1985 gf_free(cid);
1986 return GF_OK;
1987 }
1988
1989
gf_odf_read_ci(GF_BitStream * bs,GF_CIDesc * cid,u32 DescSize)1990 GF_Err gf_odf_read_ci(GF_BitStream *bs, GF_CIDesc *cid, u32 DescSize)
1991 {
1992 u32 nbBytes = 0;
1993 if (!cid) return GF_BAD_PARAM;
1994
1995 cid->compatibility = gf_bs_read_int(bs, 2); //MUST BE NULL
1996 if (cid->compatibility) return GF_ODF_INVALID_DESCRIPTOR;
1997
1998 cid->contentTypeFlag = gf_bs_read_int(bs, 1);
1999 cid->contentIdentifierFlag = gf_bs_read_int(bs, 1);
2000 cid->protectedContent = gf_bs_read_int(bs, 1);
2001 /*reserved = */gf_bs_read_int(bs, 3);
2002 nbBytes += 1;
2003
2004 if (cid->contentTypeFlag) {
2005 cid->contentType = gf_bs_read_int(bs, 8);
2006 nbBytes += 1;
2007 }
2008 if (cid->contentIdentifierFlag) {
2009 cid->contentIdentifierType = gf_bs_read_int(bs, 8);
2010 cid->contentIdentifier = (char*)gf_malloc(DescSize - 2 - cid->contentTypeFlag);
2011 if (!cid->contentIdentifier) return GF_OUT_OF_MEM;
2012
2013 gf_bs_read_data(bs, cid->contentIdentifier, DescSize - 2 - cid->contentTypeFlag);
2014 nbBytes += DescSize - 1 - cid->contentTypeFlag;
2015 }
2016 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2017 return GF_OK;
2018 }
2019
gf_odf_size_ci(GF_CIDesc * cid,u32 * outSize)2020 GF_Err gf_odf_size_ci(GF_CIDesc *cid, u32 *outSize)
2021 {
2022 if (!cid) return GF_BAD_PARAM;
2023
2024 *outSize = 1;
2025 if (cid->contentTypeFlag) *outSize += 1;
2026
2027 if (cid->contentIdentifierFlag)
2028 *outSize += (u32)strlen((const char*)cid->contentIdentifier) - 1 - cid->contentTypeFlag;
2029 return GF_OK;
2030 }
2031
gf_odf_write_ci(GF_BitStream * bs,GF_CIDesc * cid)2032 GF_Err gf_odf_write_ci(GF_BitStream *bs, GF_CIDesc *cid)
2033 {
2034 GF_Err e;
2035 u32 size;
2036 if (!cid) return GF_BAD_PARAM;
2037
2038 e = gf_odf_size_descriptor((GF_Descriptor *)cid, &size);
2039 if (e) return e;
2040 e = gf_odf_write_base_descriptor(bs, cid->tag, size);
2041 if (e) return e;
2042
2043 gf_bs_write_int(bs, cid->compatibility, 2);
2044 gf_bs_write_int(bs, cid->contentTypeFlag, 1);
2045 gf_bs_write_int(bs, cid->contentIdentifierFlag, 1);
2046 gf_bs_write_int(bs, cid->protectedContent, 1);
2047 gf_bs_write_int(bs, 7, 3); //reserved 0b111 = 7
2048
2049 if (cid->contentTypeFlag) {
2050 gf_bs_write_int(bs, cid->contentType, 8);
2051 }
2052
2053 if (cid->contentIdentifierFlag) {
2054 gf_bs_write_int(bs, cid->contentIdentifierType, 8);
2055 gf_bs_write_data(bs, cid->contentIdentifier, size - 2 - cid->contentTypeFlag);
2056 }
2057 return GF_OK;
2058 }
2059
gf_odf_new_exp_text()2060 GF_Descriptor *gf_odf_new_exp_text()
2061 {
2062 GF_ExpandedTextual *newDesc = (GF_ExpandedTextual *)gf_malloc(sizeof(GF_ExpandedTextual));
2063 if (!newDesc) return NULL;
2064
2065 newDesc->itemDescriptionList = gf_list_new();
2066 if (!newDesc->itemDescriptionList) {
2067 gf_free(newDesc);
2068 return NULL;
2069 }
2070 newDesc->itemTextList = gf_list_new();
2071 if (!newDesc->itemTextList) {
2072 gf_free(newDesc->itemDescriptionList);
2073 gf_free(newDesc);
2074 return NULL;
2075 }
2076 newDesc->isUTF8 = 0;
2077 newDesc->langCode = 0;
2078 newDesc->NonItemText = NULL;
2079 newDesc->tag = GF_ODF_TEXT_TAG;
2080 return (GF_Descriptor *)newDesc;
2081 }
2082
gf_odf_del_exp_text(GF_ExpandedTextual * etd)2083 GF_Err gf_odf_del_exp_text(GF_ExpandedTextual *etd)
2084 {
2085 if (!etd) return GF_BAD_PARAM;
2086
2087 while (gf_list_count(etd->itemDescriptionList)) {
2088 GF_ETD_ItemText *tmp = (GF_ETD_ItemText*)gf_list_get(etd->itemDescriptionList, 0);
2089 if (tmp) {
2090 if (tmp->text) gf_free(tmp->text);
2091 gf_free(tmp);
2092 }
2093 gf_list_rem(etd->itemDescriptionList, 0);
2094 }
2095 gf_list_del(etd->itemDescriptionList);
2096
2097 while (gf_list_count(etd->itemTextList)) {
2098 GF_ETD_ItemText *tmp = (GF_ETD_ItemText*)gf_list_get(etd->itemTextList, 0);
2099 if (tmp) {
2100 if (tmp->text) gf_free(tmp->text);
2101 gf_free(tmp);
2102 }
2103 gf_list_rem(etd->itemTextList, 0);
2104 }
2105 gf_list_del(etd->itemTextList);
2106
2107 if (etd->NonItemText) gf_free(etd->NonItemText);
2108 gf_free(etd);
2109 return GF_OK;
2110 }
2111
gf_odf_read_exp_text(GF_BitStream * bs,GF_ExpandedTextual * etd,u32 DescSize)2112 GF_Err gf_odf_read_exp_text(GF_BitStream *bs, GF_ExpandedTextual *etd, u32 DescSize)
2113 {
2114 GF_Err e;
2115 u32 nbBytes = 0;
2116 u32 i, len, nonLen, count;
2117 if (!etd) return GF_BAD_PARAM;
2118
2119 etd->langCode = gf_bs_read_int(bs, 24);
2120 etd->isUTF8 = gf_bs_read_int(bs, 1);
2121 /*aligned = */gf_bs_read_int(bs, 7);
2122 count = gf_bs_read_int(bs, 8);
2123 nbBytes += 5;
2124
2125 for (i = 0; i< count; i++) {
2126 //description
2127 GF_ETD_ItemText *description, *Text;
2128 description = (GF_ETD_ItemText*)gf_malloc(sizeof(GF_ETD_ItemText));
2129 if (!description) return GF_OUT_OF_MEM;
2130 description->text = NULL;
2131 e = OD_ReadUTF8String(bs, &description->text, etd->isUTF8, &len);
2132 if (e) return e;
2133 e = gf_list_add(etd->itemDescriptionList, description);
2134 if (e) return e;
2135 nbBytes += len;
2136
2137 //text
2138 Text = (GF_ETD_ItemText*)gf_malloc(sizeof(GF_ETD_ItemText));
2139 if (!Text) return GF_OUT_OF_MEM;
2140 Text->text = NULL;
2141 e = OD_ReadUTF8String(bs, &Text->text, etd->isUTF8, &len);
2142 if (e) return e;
2143 e = gf_list_add(etd->itemTextList, Text);
2144 if (e) return e;
2145 nbBytes += len;
2146 }
2147 len = gf_bs_read_int(bs, 8);
2148 nbBytes += 1;
2149 nonLen = 0;
2150 while (len == 255) {
2151 nonLen += len;
2152 len = gf_bs_read_int(bs, 8);
2153 nbBytes += 1;
2154 }
2155 nonLen += len;
2156 if (nonLen) {
2157 //here we have no choice but do the job ourselves
2158 //because the length is not encoded on 8 bits
2159 etd->NonItemText = (char *)gf_malloc(sizeof(char) * (1 + nonLen) * (etd->isUTF8 ? 1 : 2));
2160 if (!etd->NonItemText) return GF_OUT_OF_MEM;
2161 gf_bs_read_data(bs, etd->NonItemText, nonLen * (etd->isUTF8 ? 1 : 2));
2162 nbBytes += nonLen * (etd->isUTF8 ? 1 : 2);
2163 }
2164 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2165 return GF_OK;
2166 }
2167
2168
gf_odf_size_exp_text(GF_ExpandedTextual * etd,u32 * outSize)2169 GF_Err gf_odf_size_exp_text(GF_ExpandedTextual *etd, u32 *outSize)
2170 {
2171 u32 i, len, nonLen, lentmp, count;
2172 GF_ETD_ItemText *tmp;
2173 if (!etd) return GF_BAD_PARAM;
2174
2175 *outSize = 5;
2176 if (gf_list_count(etd->itemDescriptionList) != gf_list_count(etd->itemTextList)) return GF_ODF_INVALID_DESCRIPTOR;
2177
2178 count = gf_list_count(etd->itemDescriptionList);
2179 for (i = 0; i<count; i++) {
2180 tmp = (GF_ETD_ItemText *)gf_list_get(etd->itemDescriptionList, i);
2181 *outSize += OD_SizeUTF8String(tmp->text, etd->isUTF8);
2182 tmp = (GF_ETD_ItemText*)gf_list_get(etd->itemTextList, i);
2183 *outSize += OD_SizeUTF8String(tmp->text, etd->isUTF8);
2184 }
2185 *outSize += 1;
2186 if (etd->NonItemText) {
2187 if (etd->isUTF8) {
2188 nonLen = (u32)strlen((const char*)etd->NonItemText);
2189 }
2190 else {
2191 nonLen = (u32)gf_utf8_wcslen((const unsigned short*)etd->NonItemText);
2192 }
2193 }
2194 else {
2195 nonLen = 0;
2196 }
2197 len = 255;
2198 lentmp = nonLen;
2199 if (lentmp < 255) {
2200 len = lentmp;
2201 }
2202 while (len == 255) {
2203 *outSize += 1;
2204 lentmp -= 255;
2205 if (lentmp < 255) {
2206 len = lentmp;
2207 }
2208 }
2209 *outSize += nonLen * (etd->isUTF8 ? 1 : 2);
2210 return GF_OK;
2211 }
2212
gf_odf_write_exp_text(GF_BitStream * bs,GF_ExpandedTextual * etd)2213 GF_Err gf_odf_write_exp_text(GF_BitStream *bs, GF_ExpandedTextual *etd)
2214 {
2215 GF_Err e;
2216 u32 size, i, len, nonLen, lentmp, count;
2217 GF_ETD_ItemText *tmp;
2218 if (!etd) return GF_BAD_PARAM;
2219
2220 if (gf_list_count(etd->itemDescriptionList) != gf_list_count(etd->itemTextList)) return GF_ODF_INVALID_DESCRIPTOR;
2221
2222 e = gf_odf_size_descriptor((GF_Descriptor *)etd, &size);
2223 if (e) return e;
2224 e = gf_odf_write_base_descriptor(bs, etd->tag, size);
2225 if (e) return e;
2226
2227 gf_bs_write_int(bs, etd->langCode, 24);
2228 gf_bs_write_int(bs, etd->isUTF8, 1);
2229 gf_bs_write_int(bs, 0, 7); //aligned
2230 gf_bs_write_int(bs, gf_list_count(etd->itemDescriptionList), 8);
2231
2232 count = gf_list_count(etd->itemDescriptionList);
2233 for (i = 0; i<count; i++) {
2234 tmp = (GF_ETD_ItemText *)gf_list_get(etd->itemDescriptionList, i);
2235 OD_WriteUTF8String(bs, tmp->text, etd->isUTF8);
2236 tmp = (GF_ETD_ItemText*)gf_list_get(etd->itemTextList, i);
2237 OD_WriteUTF8String(bs, tmp->text, etd->isUTF8);
2238 }
2239 if (etd->NonItemText) {
2240 if (etd->isUTF8) {
2241 nonLen = (u32)strlen((const char*)etd->NonItemText);
2242 }
2243 else {
2244 nonLen = (u32)gf_utf8_wcslen((const unsigned short*)etd->NonItemText);
2245 }
2246 }
2247 else {
2248 nonLen = 0;
2249 }
2250 lentmp = nonLen;
2251 len = lentmp < 255 ? lentmp : 255;
2252 while (len == 255) {
2253 gf_bs_write_int(bs, len, 8);
2254 lentmp -= len;
2255 len = lentmp < 255 ? lentmp : 255;
2256 }
2257 gf_bs_write_int(bs, len, 8);
2258 gf_bs_write_data(bs, etd->NonItemText, nonLen * (etd->isUTF8 ? 1 : 2));
2259 return GF_OK;
2260 }
2261
gf_odf_new_pl_ext()2262 GF_Descriptor *gf_odf_new_pl_ext()
2263 {
2264 GF_PLExt *newDesc = (GF_PLExt *)gf_malloc(sizeof(GF_PLExt));
2265 if (!newDesc) return NULL;
2266 newDesc->AudioProfileLevelIndication = 0;
2267 newDesc->GraphicsProfileLevelIndication = 0;
2268 newDesc->MPEGJProfileLevelIndication = 0;
2269 newDesc->ODProfileLevelIndication = 0;
2270 newDesc->profileLevelIndicationIndex = 0;
2271 newDesc->SceneProfileLevelIndication = 0;
2272 newDesc->VisualProfileLevelIndication = 0;
2273 newDesc->tag = GF_ODF_EXT_PL_TAG;
2274 return (GF_Descriptor *)newDesc;
2275 }
2276
gf_odf_del_pl_ext(GF_PLExt * pld)2277 GF_Err gf_odf_del_pl_ext(GF_PLExt *pld)
2278 {
2279 if (!pld) return GF_BAD_PARAM;
2280
2281 gf_free(pld);
2282 return GF_OK;
2283 }
2284
gf_odf_read_pl_ext(GF_BitStream * bs,GF_PLExt * pld,u32 DescSize)2285 GF_Err gf_odf_read_pl_ext(GF_BitStream *bs, GF_PLExt *pld, u32 DescSize)
2286 {
2287 u32 nbBytes = 0;
2288 if (!pld) return GF_BAD_PARAM;
2289
2290 pld->profileLevelIndicationIndex = gf_bs_read_int(bs, 8);
2291 pld->ODProfileLevelIndication = gf_bs_read_int(bs, 8);
2292 pld->SceneProfileLevelIndication = gf_bs_read_int(bs, 8);
2293 pld->AudioProfileLevelIndication = gf_bs_read_int(bs, 8);
2294 pld->VisualProfileLevelIndication = gf_bs_read_int(bs, 8);
2295 pld->GraphicsProfileLevelIndication = gf_bs_read_int(bs, 8);
2296 pld->MPEGJProfileLevelIndication = gf_bs_read_int(bs, 8);
2297
2298 nbBytes += 7;
2299 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2300 return GF_OK;
2301 }
2302
gf_odf_size_pl_ext(GF_PLExt * pld,u32 * outSize)2303 GF_Err gf_odf_size_pl_ext(GF_PLExt *pld, u32 *outSize)
2304 {
2305 if (!pld) return GF_BAD_PARAM;
2306
2307 *outSize = 7;
2308 return GF_OK;
2309 }
2310
gf_odf_write_pl_ext(GF_BitStream * bs,GF_PLExt * pld)2311 GF_Err gf_odf_write_pl_ext(GF_BitStream *bs, GF_PLExt *pld)
2312 {
2313 GF_Err e;
2314 u32 size;
2315 if (!pld) return GF_BAD_PARAM;
2316
2317 e = gf_odf_size_descriptor((GF_Descriptor *)pld, &size);
2318 if (e) return e;
2319 e = gf_odf_write_base_descriptor(bs, pld->tag, size);
2320 if (e) return e;
2321
2322 gf_bs_write_int(bs, pld->profileLevelIndicationIndex, 8);
2323 gf_bs_write_int(bs, pld->ODProfileLevelIndication, 8);
2324 gf_bs_write_int(bs, pld->SceneProfileLevelIndication, 8);
2325 gf_bs_write_int(bs, pld->AudioProfileLevelIndication, 8);
2326 gf_bs_write_int(bs, pld->VisualProfileLevelIndication, 8);
2327 gf_bs_write_int(bs, pld->GraphicsProfileLevelIndication, 8);
2328 gf_bs_write_int(bs, pld->MPEGJProfileLevelIndication, 8);
2329 return GF_OK;
2330 }
2331
gf_odf_new_ipi_ptr()2332 GF_Descriptor *gf_odf_new_ipi_ptr()
2333 {
2334 GF_IPIPtr *newDesc = (GF_IPIPtr *)gf_malloc(sizeof(GF_IPIPtr));
2335 if (!newDesc) return NULL;
2336 newDesc->IPI_ES_Id = 0;
2337 newDesc->tag = GF_ODF_IPI_PTR_TAG;
2338 return (GF_Descriptor *)newDesc;
2339 }
2340
gf_odf_del_ipi_ptr(GF_IPIPtr * ipid)2341 GF_Err gf_odf_del_ipi_ptr(GF_IPIPtr *ipid)
2342 {
2343 if (!ipid) return GF_BAD_PARAM;
2344 gf_free(ipid);
2345 return GF_OK;
2346 }
2347
gf_odf_read_ipi_ptr(GF_BitStream * bs,GF_IPIPtr * ipid,u32 DescSize)2348 GF_Err gf_odf_read_ipi_ptr(GF_BitStream *bs, GF_IPIPtr *ipid, u32 DescSize)
2349 {
2350 u32 nbBytes = 0;
2351 if (!ipid) return GF_BAD_PARAM;
2352
2353 ipid->IPI_ES_Id = gf_bs_read_int(bs, 16);
2354 nbBytes += 2;
2355 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2356 return GF_OK;
2357 }
2358
gf_odf_size_ipi_ptr(GF_IPIPtr * ipid,u32 * outSize)2359 GF_Err gf_odf_size_ipi_ptr(GF_IPIPtr *ipid, u32 *outSize)
2360 {
2361 if (!ipid) return GF_BAD_PARAM;
2362 *outSize = 2;
2363 return GF_OK;
2364 }
2365
gf_odf_write_ipi_ptr(GF_BitStream * bs,GF_IPIPtr * ipid)2366 GF_Err gf_odf_write_ipi_ptr(GF_BitStream *bs, GF_IPIPtr *ipid)
2367 {
2368 GF_Err e;
2369 u32 size;
2370 if (!ipid) return GF_BAD_PARAM;
2371 e = gf_odf_size_descriptor((GF_Descriptor *)ipid, &size);
2372 if (e) return e;
2373 e = gf_odf_write_base_descriptor(bs, ipid->tag, size);
2374 if (e) return e;
2375 gf_bs_write_int(bs, ipid->IPI_ES_Id, 16);
2376 return GF_OK;
2377 }
2378
gf_odf_new_ipmp()2379 GF_Descriptor *gf_odf_new_ipmp()
2380 {
2381 GF_IPMP_Descriptor *newDesc;
2382 GF_SAFEALLOC(newDesc, GF_IPMP_Descriptor);
2383 if (!newDesc) return NULL;
2384
2385 newDesc->ipmpx_data = gf_list_new();
2386 newDesc->tag = GF_ODF_IPMP_TAG;
2387 return (GF_Descriptor *)newDesc;
2388 }
gf_odf_del_ipmp(GF_IPMP_Descriptor * ipmp)2389 GF_Err gf_odf_del_ipmp(GF_IPMP_Descriptor *ipmp)
2390 {
2391 if (!ipmp) return GF_BAD_PARAM;
2392 if (ipmp->opaque_data) gf_free(ipmp->opaque_data);
2393 #ifndef GPAC_MINIMAL_ODF
2394 /*TODO DELETE IPMPX*/
2395 while (gf_list_count(ipmp->ipmpx_data)) {
2396 GF_IPMPX_Data *p = (GF_IPMPX_Data *)gf_list_get(ipmp->ipmpx_data, 0);
2397 gf_list_rem(ipmp->ipmpx_data, 0);
2398 gf_ipmpx_data_del(p);
2399 }
2400 #endif
2401 gf_list_del(ipmp->ipmpx_data);
2402 gf_free(ipmp);
2403 return GF_OK;
2404 }
2405
gf_odf_read_ipmp(GF_BitStream * bs,GF_IPMP_Descriptor * ipmp,u32 DescSize)2406 GF_Err gf_odf_read_ipmp(GF_BitStream *bs, GF_IPMP_Descriptor *ipmp, u32 DescSize)
2407 {
2408 u32 size;
2409 u64 nbBytes = 0;
2410 if (!ipmp) return GF_BAD_PARAM;
2411
2412 ipmp->IPMP_DescriptorID = gf_bs_read_int(bs, 8);
2413 ipmp->IPMPS_Type = gf_bs_read_int(bs, 16);
2414 nbBytes += 3;
2415 size = DescSize - 3;
2416
2417 /*IPMPX escape*/
2418 if ((ipmp->IPMP_DescriptorID == 0xFF) && (ipmp->IPMPS_Type == 0xFFFF)) {
2419 ipmp->IPMP_DescriptorIDEx = gf_bs_read_int(bs, 16);
2420 gf_bs_read_data(bs, (char*)ipmp->IPMP_ToolID, 16);
2421 ipmp->control_point = gf_bs_read_int(bs, 8);
2422 nbBytes += 19;
2423 if (ipmp->control_point) {
2424 ipmp->cp_sequence_code = gf_bs_read_int(bs, 8);
2425 nbBytes += 1;
2426 }
2427 while (nbBytes<DescSize) {
2428 u64 pos;
2429 GF_Err e;
2430 GF_IPMPX_Data *p;
2431 pos = gf_bs_get_position(bs);
2432 e = gf_ipmpx_data_parse(bs, &p);
2433 if (e) return e;
2434 gf_list_add(ipmp->ipmpx_data, p);
2435 nbBytes += gf_bs_get_position(bs) - pos;
2436 }
2437 }
2438 /*URL*/
2439 else if (!ipmp->IPMPS_Type) {
2440 ipmp->opaque_data = (char*)gf_malloc(size + 1);
2441 if (!ipmp->opaque_data) return GF_OUT_OF_MEM;
2442 gf_bs_read_data(bs, ipmp->opaque_data, size);
2443 nbBytes += size;
2444 ipmp->opaque_data[size] = 0;
2445 ipmp->opaque_data_size = size;
2446
2447 }
2448 /*data*/
2449 else {
2450 ipmp->opaque_data_size = size;
2451 ipmp->opaque_data = (char*)gf_malloc(size);
2452 if (!ipmp->opaque_data) return GF_OUT_OF_MEM;
2453 gf_bs_read_data(bs, ipmp->opaque_data, size);
2454 nbBytes += size;
2455 }
2456 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2457 return GF_OK;
2458 }
2459
gf_odf_size_ipmp(GF_IPMP_Descriptor * ipmp,u32 * outSize)2460 GF_Err gf_odf_size_ipmp(GF_IPMP_Descriptor *ipmp, u32 *outSize)
2461 {
2462 u32 i, s;
2463 if (!ipmp) return GF_BAD_PARAM;
2464
2465 *outSize = 3;
2466 /*IPMPX escape*/
2467 if ((ipmp->IPMP_DescriptorID == 0xFF) && (ipmp->IPMPS_Type == 0xFFFF)) {
2468 GF_IPMPX_Data *p;
2469 *outSize += 19;
2470 if (ipmp->control_point) *outSize += 1;
2471 s = 0;
2472 i = 0;
2473 while ((p = (GF_IPMPX_Data *)gf_list_enum(ipmp->ipmpx_data, &i))) {
2474 s += gf_ipmpx_data_full_size(p);
2475 }
2476 (*outSize) += s;
2477 }
2478 else if (!ipmp->IPMPS_Type) {
2479 if (!ipmp->opaque_data) return GF_ODF_INVALID_DESCRIPTOR;
2480 *outSize += (u32)strlen(ipmp->opaque_data);
2481 }
2482 else {
2483 *outSize += ipmp->opaque_data_size;
2484 }
2485 return GF_OK;
2486 }
2487
gf_odf_write_ipmp(GF_BitStream * bs,GF_IPMP_Descriptor * ipmp)2488 GF_Err gf_odf_write_ipmp(GF_BitStream *bs, GF_IPMP_Descriptor *ipmp)
2489 {
2490 GF_Err e;
2491 u32 size, i;
2492 if (!ipmp) return GF_BAD_PARAM;
2493
2494 e = gf_odf_size_descriptor((GF_Descriptor *)ipmp, &size);
2495 if (e) return e;
2496 e = gf_odf_write_base_descriptor(bs, ipmp->tag, size);
2497 if (e) return e;
2498 gf_bs_write_int(bs, ipmp->IPMP_DescriptorID, 8);
2499 gf_bs_write_int(bs, ipmp->IPMPS_Type, 16);
2500
2501 if ((ipmp->IPMP_DescriptorID == 0xFF) && (ipmp->IPMPS_Type == 0xFFFF)) {
2502 GF_IPMPX_Data *p;
2503 gf_bs_write_int(bs, ipmp->IPMP_DescriptorIDEx, 16);
2504 gf_bs_write_data(bs, (char*)ipmp->IPMP_ToolID, 16);
2505 gf_bs_write_int(bs, ipmp->control_point, 8);
2506 if (ipmp->control_point) gf_bs_write_int(bs, ipmp->cp_sequence_code, 8);
2507
2508 i = 0;
2509 while ((p = (GF_IPMPX_Data *)gf_list_enum(ipmp->ipmpx_data, &i))) {
2510 gf_ipmpx_data_write(bs, p);
2511 }
2512 }
2513 else if (!ipmp->IPMPS_Type) {
2514 if (!ipmp->opaque_data) return GF_ODF_INVALID_DESCRIPTOR;
2515 gf_bs_write_data(bs, ipmp->opaque_data, (u32)strlen(ipmp->opaque_data));
2516 }
2517 else {
2518 gf_bs_write_data(bs, ipmp->opaque_data, ipmp->opaque_data_size);
2519 }
2520 return GF_OK;
2521 }
2522
gf_odf_new_ipmp_ptr()2523 GF_Descriptor *gf_odf_new_ipmp_ptr()
2524 {
2525 GF_IPMPPtr *newDesc;
2526 GF_SAFEALLOC(newDesc, GF_IPMPPtr);
2527 if (!newDesc) return NULL;
2528 newDesc->tag = GF_ODF_IPMP_PTR_TAG;
2529 return (GF_Descriptor *)newDesc;
2530 }
gf_odf_del_ipmp_ptr(GF_IPMPPtr * ipmpd)2531 GF_Err gf_odf_del_ipmp_ptr(GF_IPMPPtr *ipmpd)
2532 {
2533 if (!ipmpd) return GF_BAD_PARAM;
2534 gf_free(ipmpd);
2535 return GF_OK;
2536 }
2537
gf_odf_read_ipmp_ptr(GF_BitStream * bs,GF_IPMPPtr * ipmpd,u32 DescSize)2538 GF_Err gf_odf_read_ipmp_ptr(GF_BitStream *bs, GF_IPMPPtr *ipmpd, u32 DescSize)
2539 {
2540 u32 nbBytes = 0;
2541 if (!ipmpd) return GF_BAD_PARAM;
2542 ipmpd->IPMP_DescriptorID = gf_bs_read_int(bs, 8);
2543 nbBytes += 1;
2544 if (ipmpd->IPMP_DescriptorID == 0xFF) {
2545 ipmpd->IPMP_DescriptorIDEx = gf_bs_read_int(bs, 16);
2546 ipmpd->IPMP_ES_ID = gf_bs_read_int(bs, 16);
2547 nbBytes += 4;
2548 }
2549 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2550 return GF_OK;
2551 }
gf_odf_size_ipmp_ptr(GF_IPMPPtr * ipmpd,u32 * outSize)2552 GF_Err gf_odf_size_ipmp_ptr(GF_IPMPPtr *ipmpd, u32 *outSize)
2553 {
2554 if (!ipmpd) return GF_BAD_PARAM;
2555 *outSize = 1;
2556 if (ipmpd->IPMP_DescriptorID == 0xFF) *outSize += 4;
2557 return GF_OK;
2558 }
gf_odf_write_ipmp_ptr(GF_BitStream * bs,GF_IPMPPtr * ipmpd)2559 GF_Err gf_odf_write_ipmp_ptr(GF_BitStream *bs, GF_IPMPPtr *ipmpd)
2560 {
2561 GF_Err e;
2562 u32 size;
2563 if (!ipmpd) return GF_BAD_PARAM;
2564
2565 e = gf_odf_size_descriptor((GF_Descriptor *)ipmpd, &size);
2566 if (e) return e;
2567 e = gf_odf_write_base_descriptor(bs, ipmpd->tag, size);
2568 if (e) return e;
2569 gf_bs_write_int(bs, ipmpd->IPMP_DescriptorID, 8);
2570 if (ipmpd->IPMP_DescriptorID == 0xFF) {
2571 gf_bs_write_int(bs, ipmpd->IPMP_DescriptorIDEx, 16);
2572 gf_bs_write_int(bs, ipmpd->IPMP_ES_ID, 16);
2573 }
2574 return GF_OK;
2575 }
2576
gf_odf_new_kw()2577 GF_Descriptor *gf_odf_new_kw()
2578 {
2579 GF_KeyWord *newDesc = (GF_KeyWord *)gf_malloc(sizeof(GF_KeyWord));
2580 if (!newDesc) return NULL;
2581
2582 newDesc->keyWordsList = gf_list_new();
2583 if (!newDesc->keyWordsList) {
2584 gf_free(newDesc);
2585 return NULL;
2586 }
2587 newDesc->isUTF8 = 0;
2588 newDesc->languageCode = 0;
2589 newDesc->tag = GF_ODF_KW_TAG;
2590 return (GF_Descriptor *)newDesc;
2591 }
2592
gf_odf_del_kw(GF_KeyWord * kwd)2593 GF_Err gf_odf_del_kw(GF_KeyWord *kwd)
2594 {
2595 if (!kwd) return GF_BAD_PARAM;
2596
2597 while (gf_list_count(kwd->keyWordsList)) {
2598 GF_KeyWordItem *tmp = (GF_KeyWordItem*)gf_list_get(kwd->keyWordsList, 0);
2599 if (tmp) {
2600 if (tmp->keyWord) gf_free(tmp->keyWord);
2601 gf_free(tmp);
2602 }
2603 }
2604 gf_list_del(kwd->keyWordsList);
2605 gf_free(kwd);
2606 return GF_OK;
2607 }
2608
gf_odf_read_kw(GF_BitStream * bs,GF_KeyWord * kwd,u32 DescSize)2609 GF_Err gf_odf_read_kw(GF_BitStream *bs, GF_KeyWord *kwd, u32 DescSize)
2610 {
2611 GF_Err e;
2612 u32 nbBytes = 0, i, kwcount, len;
2613 if (!kwd) return GF_BAD_PARAM;
2614
2615 kwd->languageCode = gf_bs_read_int(bs, 24);
2616 kwd->isUTF8 = gf_bs_read_int(bs, 1);
2617 /*aligned = */gf_bs_read_int(bs, 7);
2618 kwcount = gf_bs_read_int(bs, 8);
2619 nbBytes += 5;
2620
2621 for (i = 0; i < kwcount; i++) {
2622 GF_KeyWordItem *tmp = (GF_KeyWordItem*)gf_malloc(sizeof(GF_KeyWordItem));
2623 if (!tmp) return GF_OUT_OF_MEM;
2624 e = OD_ReadUTF8String(bs, &tmp->keyWord, kwd->isUTF8, &len);
2625 if (e) return e;
2626 e = gf_list_add(kwd->keyWordsList, tmp);
2627 if (e) return e;
2628 nbBytes += len;
2629 }
2630 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2631 return GF_OK;
2632 }
2633
2634
gf_odf_size_kw(GF_KeyWord * kwd,u32 * outSize)2635 GF_Err gf_odf_size_kw(GF_KeyWord *kwd, u32 *outSize)
2636 {
2637 u32 i;
2638 GF_KeyWordItem *tmp;
2639 if (!kwd) return GF_BAD_PARAM;
2640
2641 *outSize = 5;
2642 i = 0;
2643 while ((tmp = (GF_KeyWordItem *)gf_list_enum(kwd->keyWordsList, &i))) {
2644 *outSize += OD_SizeUTF8String(tmp->keyWord, kwd->isUTF8);
2645 }
2646 return GF_OK;
2647 }
gf_odf_write_kw(GF_BitStream * bs,GF_KeyWord * kwd)2648 GF_Err gf_odf_write_kw(GF_BitStream *bs, GF_KeyWord *kwd)
2649 {
2650 GF_Err e;
2651 u32 size, i;
2652 GF_KeyWordItem *tmp;
2653 if (!kwd) return GF_BAD_PARAM;
2654
2655 e = gf_odf_size_descriptor((GF_Descriptor *)kwd, &size);
2656 if (e) return e;
2657 e = gf_odf_write_base_descriptor(bs, kwd->tag, size);
2658 if (e) return e;
2659
2660 gf_bs_write_int(bs, kwd->languageCode, 24);
2661 gf_bs_write_int(bs, kwd->isUTF8, 1);
2662 gf_bs_write_int(bs, 0, 7); //aligned(8)
2663 gf_bs_write_int(bs, gf_list_count(kwd->keyWordsList), 8);
2664
2665 i = 0;
2666 while ((tmp = (GF_KeyWordItem *)gf_list_enum(kwd->keyWordsList, &i))) {
2667 OD_WriteUTF8String(bs, tmp->keyWord, kwd->isUTF8);
2668 }
2669 return GF_OK;
2670 }
2671
gf_odf_new_oci_date()2672 GF_Descriptor *gf_odf_new_oci_date()
2673 {
2674 GF_OCI_Data *newDesc = (GF_OCI_Data *)gf_malloc(sizeof(GF_OCI_Data));
2675 if (!newDesc) return NULL;
2676 memset(newDesc->OCICreationDate, 0, 5);
2677 newDesc->tag = GF_ODF_OCI_DATE_TAG;
2678 return (GF_Descriptor *)newDesc;
2679 }
2680
gf_odf_del_oci_date(GF_OCI_Data * ocd)2681 GF_Err gf_odf_del_oci_date(GF_OCI_Data *ocd)
2682 {
2683 if (!ocd) return GF_BAD_PARAM;
2684 gf_free(ocd);
2685 return GF_OK;
2686 }
2687
gf_odf_read_oci_date(GF_BitStream * bs,GF_OCI_Data * ocd,u32 DescSize)2688 GF_Err gf_odf_read_oci_date(GF_BitStream *bs, GF_OCI_Data *ocd, u32 DescSize)
2689 {
2690 u32 nbBytes = 0;
2691 if (!ocd) return GF_BAD_PARAM;
2692
2693 gf_bs_read_data(bs, ocd->OCICreationDate, DATE_CODING_BIT_LEN);
2694 nbBytes += DATE_CODING_BIT_LEN / 8;
2695 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2696 return GF_OK;
2697 }
2698
gf_odf_size_oci_date(GF_OCI_Data * ocd,u32 * outSize)2699 GF_Err gf_odf_size_oci_date(GF_OCI_Data *ocd, u32 *outSize)
2700 {
2701 if (!ocd) return GF_BAD_PARAM;
2702 *outSize = (DATE_CODING_BIT_LEN / 8);
2703 return GF_OK;
2704 }
2705
gf_odf_write_oci_date(GF_BitStream * bs,GF_OCI_Data * ocd)2706 GF_Err gf_odf_write_oci_date(GF_BitStream *bs, GF_OCI_Data *ocd)
2707 {
2708 GF_Err e;
2709 u32 size;
2710 if (!ocd) return GF_BAD_PARAM;
2711
2712 e = gf_odf_size_descriptor((GF_Descriptor *)ocd, &size);
2713 if (e) return e;
2714 e = gf_odf_write_base_descriptor(bs, ocd->tag, size);
2715 if (e) return e;
2716 gf_bs_write_data(bs, ocd->OCICreationDate, DATE_CODING_BIT_LEN);
2717 return GF_OK;
2718 }
2719
gf_odf_new_oci_name()2720 GF_Descriptor *gf_odf_new_oci_name()
2721 {
2722 GF_OCICreators *newDesc = (GF_OCICreators *)gf_malloc(sizeof(GF_OCICreators));
2723 if (!newDesc) return NULL;
2724
2725 newDesc->OCICreators = gf_list_new();
2726 if (!newDesc->OCICreators) {
2727 gf_free(newDesc);
2728 return NULL;
2729 }
2730 newDesc->tag = GF_ODF_OCI_NAME_TAG;
2731 return (GF_Descriptor *)newDesc;
2732 }
gf_odf_del_oci_name(GF_OCICreators * ocn)2733 GF_Err gf_odf_del_oci_name(GF_OCICreators *ocn)
2734 {
2735 u32 i;
2736 GF_OCICreator_item *tmp;
2737 if (!ocn) return GF_BAD_PARAM;
2738
2739 i = 0;
2740 while ((tmp = (GF_OCICreator_item *)gf_list_enum(ocn->OCICreators, &i))) {
2741 if (tmp->OCICreatorName) gf_free(tmp->OCICreatorName);
2742 gf_free(tmp);
2743 }
2744 gf_list_del(ocn->OCICreators);
2745 gf_free(ocn);
2746 return GF_OK;
2747 }
2748
gf_odf_read_oci_name(GF_BitStream * bs,GF_OCICreators * ocn,u32 DescSize)2749 GF_Err gf_odf_read_oci_name(GF_BitStream *bs, GF_OCICreators *ocn, u32 DescSize)
2750 {
2751 GF_Err e;
2752 u32 nbBytes = 0;
2753 u32 i, count, len;
2754 if (!ocn) return GF_BAD_PARAM;
2755
2756 count = gf_bs_read_int(bs, 8);
2757 nbBytes += 1;
2758 for (i = 0; i< count; i++) {
2759 GF_OCICreator_item *tmp = (GF_OCICreator_item*)gf_malloc(sizeof(GF_OCICreator_item));
2760 if (!tmp) return GF_OUT_OF_MEM;
2761 tmp->langCode = gf_bs_read_int(bs, 24);
2762 tmp->isUTF8 = gf_bs_read_int(bs, 1);
2763 /*aligned = */gf_bs_read_int(bs, 7);
2764 nbBytes += 4;
2765 e = OD_ReadUTF8String(bs, &tmp->OCICreatorName, tmp->isUTF8, &len);
2766 if (e) return e;
2767 nbBytes += len;
2768 e = gf_list_add(ocn->OCICreators, tmp);
2769 if (e) return e;
2770 }
2771 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2772 return GF_OK;
2773 }
2774
gf_odf_size_oci_name(GF_OCICreators * ocn,u32 * outSize)2775 GF_Err gf_odf_size_oci_name(GF_OCICreators *ocn, u32 *outSize)
2776 {
2777 u32 i;
2778 GF_OCICreator_item *tmp;
2779 if (!ocn) return GF_BAD_PARAM;
2780
2781 *outSize = 1;
2782 i = 0;
2783 while ((tmp = (GF_OCICreator_item *)gf_list_enum(ocn->OCICreators, &i))) {
2784 *outSize += 4 + OD_SizeUTF8String(tmp->OCICreatorName, tmp->isUTF8);
2785 }
2786 return GF_OK;
2787 }
2788
gf_odf_write_oci_name(GF_BitStream * bs,GF_OCICreators * ocn)2789 GF_Err gf_odf_write_oci_name(GF_BitStream *bs, GF_OCICreators *ocn)
2790 {
2791 GF_Err e;
2792 u32 size;
2793 u32 i;
2794 GF_OCICreator_item *tmp;
2795 if (!ocn) return GF_BAD_PARAM;
2796
2797 e = gf_odf_size_descriptor((GF_Descriptor *)ocn, &size);
2798 if (e) return e;
2799 e = gf_odf_write_base_descriptor(bs, ocn->tag, size);
2800 if (e) return e;
2801 gf_bs_write_int(bs, gf_list_count(ocn->OCICreators), 8);
2802
2803 i = 0;
2804 while ((tmp = (GF_OCICreator_item *)gf_list_enum(ocn->OCICreators, &i))) {
2805 gf_bs_write_int(bs, tmp->langCode, 24);
2806 gf_bs_write_int(bs, tmp->isUTF8, 1);
2807 gf_bs_write_int(bs, 0, 7); //aligned
2808 gf_bs_write_int(bs, (u32)strlen(tmp->OCICreatorName), 8);
2809 OD_WriteUTF8String(bs, tmp->OCICreatorName, tmp->isUTF8);
2810 }
2811 return GF_OK;
2812 }
2813
2814
gf_odf_new_pl_idx()2815 GF_Descriptor *gf_odf_new_pl_idx()
2816 {
2817 GF_PL_IDX *newDesc = (GF_PL_IDX *)gf_malloc(sizeof(GF_PL_IDX));
2818 if (!newDesc) return NULL;
2819 newDesc->profileLevelIndicationIndex = 0;
2820 newDesc->tag = GF_ODF_PL_IDX_TAG;
2821 return (GF_Descriptor *)newDesc;
2822 }
2823
gf_odf_del_pl_idx(GF_PL_IDX * plid)2824 GF_Err gf_odf_del_pl_idx(GF_PL_IDX *plid)
2825 {
2826 if (!plid) return GF_BAD_PARAM;
2827 gf_free(plid);
2828 return GF_OK;
2829 }
2830
gf_odf_read_pl_idx(GF_BitStream * bs,GF_PL_IDX * plid,u32 DescSize)2831 GF_Err gf_odf_read_pl_idx(GF_BitStream *bs, GF_PL_IDX *plid, u32 DescSize)
2832 {
2833 u32 nbBytes = 0;
2834 if (!plid) return GF_BAD_PARAM;
2835
2836 plid->profileLevelIndicationIndex = gf_bs_read_int(bs, 8);
2837 nbBytes += 1;
2838 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2839 return GF_OK;
2840 }
gf_odf_size_pl_idx(GF_PL_IDX * plid,u32 * outSize)2841 GF_Err gf_odf_size_pl_idx(GF_PL_IDX *plid, u32 *outSize)
2842 {
2843 if (!plid) return GF_BAD_PARAM;
2844 *outSize = 1;
2845 return GF_OK;
2846 }
gf_odf_write_pl_idx(GF_BitStream * bs,GF_PL_IDX * plid)2847 GF_Err gf_odf_write_pl_idx(GF_BitStream *bs, GF_PL_IDX *plid)
2848 {
2849 GF_Err e;
2850 u32 size;
2851 if (!plid) return GF_BAD_PARAM;
2852 e = gf_odf_size_descriptor((GF_Descriptor *)plid, &size);
2853 if (e) return e;
2854 e = gf_odf_write_base_descriptor(bs, plid->tag, size);
2855 if (e) return e;
2856 gf_bs_write_int(bs, plid->profileLevelIndicationIndex, 8);
2857 return GF_OK;
2858 }
2859
2860
gf_odf_new_rating()2861 GF_Descriptor *gf_odf_new_rating()
2862 {
2863 GF_Rating *newDesc = (GF_Rating *)gf_malloc(sizeof(GF_Rating));
2864 if (!newDesc) return NULL;
2865
2866 newDesc->infoLength = 0;
2867 newDesc->ratingInfo = NULL;
2868 newDesc->ratingCriteria = 0;
2869 newDesc->ratingEntity = 0;
2870 newDesc->tag = GF_ODF_RATING_TAG;
2871 return (GF_Descriptor *)newDesc;
2872 }
2873
gf_odf_del_rating(GF_Rating * rd)2874 GF_Err gf_odf_del_rating(GF_Rating *rd)
2875 {
2876 if (!rd) return GF_BAD_PARAM;
2877
2878 if (rd->ratingInfo) gf_free(rd->ratingInfo);
2879 gf_free(rd);
2880 return GF_OK;
2881 }
2882
gf_odf_read_rating(GF_BitStream * bs,GF_Rating * rd,u32 DescSize)2883 GF_Err gf_odf_read_rating(GF_BitStream *bs, GF_Rating *rd, u32 DescSize)
2884 {
2885 u32 nbBytes = 0;
2886 if (!rd) return GF_BAD_PARAM;
2887
2888 rd->ratingEntity = gf_bs_read_int(bs, 32);
2889 rd->ratingCriteria = gf_bs_read_int(bs, 16);
2890 rd->infoLength = DescSize - 6;
2891 nbBytes += 6;
2892
2893 rd->ratingInfo = (char*)gf_malloc(rd->infoLength);
2894 if (!rd->ratingInfo) return GF_OUT_OF_MEM;
2895 gf_bs_read_data(bs, rd->ratingInfo, rd->infoLength);
2896 nbBytes += rd->infoLength;
2897 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2898 return GF_OK;
2899 }
2900
gf_odf_size_rating(GF_Rating * rd,u32 * outSize)2901 GF_Err gf_odf_size_rating(GF_Rating *rd, u32 *outSize)
2902 {
2903 if (!rd) return GF_BAD_PARAM;
2904
2905 *outSize = 6 + rd->infoLength;
2906 return GF_OK;
2907 }
2908
gf_odf_write_rating(GF_BitStream * bs,GF_Rating * rd)2909 GF_Err gf_odf_write_rating(GF_BitStream *bs, GF_Rating *rd)
2910 {
2911 GF_Err e;
2912 u32 size;
2913 if (!rd) return GF_BAD_PARAM;
2914 e = gf_odf_size_descriptor((GF_Descriptor *)rd, &size);
2915 if (e) return e;
2916 e = gf_odf_write_base_descriptor(bs, rd->tag, size);
2917 if (e) return e;
2918 gf_bs_write_int(bs, rd->ratingEntity, 32);
2919 gf_bs_write_int(bs, rd->ratingCriteria, 16);
2920 gf_bs_write_data(bs, rd->ratingInfo, rd->infoLength);
2921 return GF_OK;
2922 }
2923
2924
gf_odf_new_reg()2925 GF_Descriptor *gf_odf_new_reg()
2926 {
2927 GF_Registration *newDesc = (GF_Registration *)gf_malloc(sizeof(GF_Registration));
2928 if (!newDesc) return NULL;
2929 newDesc->additionalIdentificationInfo = NULL;
2930 newDesc->dataLength = 0;
2931 newDesc->formatIdentifier = 0;
2932 newDesc->tag = GF_ODF_REG_TAG;
2933 return (GF_Descriptor *)newDesc;
2934 }
2935
gf_odf_del_reg(GF_Registration * reg)2936 GF_Err gf_odf_del_reg(GF_Registration *reg)
2937 {
2938 if (!reg) return GF_BAD_PARAM;
2939
2940 if (reg->additionalIdentificationInfo) gf_free(reg->additionalIdentificationInfo);
2941 gf_free(reg);
2942 return GF_OK;
2943 }
2944
gf_odf_read_reg(GF_BitStream * bs,GF_Registration * reg,u32 DescSize)2945 GF_Err gf_odf_read_reg(GF_BitStream *bs, GF_Registration *reg, u32 DescSize)
2946 {
2947 u32 nbBytes = 0;
2948 if (!reg) return GF_BAD_PARAM;
2949
2950 reg->formatIdentifier = gf_bs_read_int(bs, 32);
2951 reg->dataLength = DescSize - 4;
2952 reg->additionalIdentificationInfo = (char*)gf_malloc(reg->dataLength);
2953 if (!reg->additionalIdentificationInfo) return GF_OUT_OF_MEM;
2954 gf_bs_read_data(bs, reg->additionalIdentificationInfo, reg->dataLength);
2955 nbBytes += reg->dataLength + 4;
2956 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
2957 return GF_OK;
2958 }
2959
2960
gf_odf_size_reg(GF_Registration * reg,u32 * outSize)2961 GF_Err gf_odf_size_reg(GF_Registration *reg, u32 *outSize)
2962 {
2963 if (!reg) return GF_BAD_PARAM;
2964
2965 *outSize = 4 + reg->dataLength;
2966 return GF_OK;
2967 }
2968
gf_odf_write_reg(GF_BitStream * bs,GF_Registration * reg)2969 GF_Err gf_odf_write_reg(GF_BitStream *bs, GF_Registration *reg)
2970 {
2971 GF_Err e;
2972 u32 size;
2973 if (!reg) return GF_BAD_PARAM;
2974
2975 e = gf_odf_size_descriptor((GF_Descriptor *)reg, &size);
2976 if (e) return e;
2977 e = gf_odf_write_base_descriptor(bs, reg->tag, size);
2978 if (e) return e;
2979
2980 gf_bs_write_int(bs, reg->formatIdentifier, 32);
2981 gf_bs_write_data(bs, reg->additionalIdentificationInfo, reg->dataLength);
2982 return GF_OK;
2983 }
2984
gf_odf_new_short_text()2985 GF_Descriptor *gf_odf_new_short_text()
2986 {
2987 GF_ShortTextual *newDesc = (GF_ShortTextual *)gf_malloc(sizeof(GF_ShortTextual));
2988 if (!newDesc) return NULL;
2989
2990 newDesc->eventName = NULL;
2991 newDesc->eventText = NULL;
2992 newDesc->isUTF8 = 0;
2993 newDesc->langCode = 0;
2994 newDesc->tag = GF_ODF_SHORT_TEXT_TAG;
2995 return (GF_Descriptor *)newDesc;
2996 }
2997
gf_odf_del_short_text(GF_ShortTextual * std)2998 GF_Err gf_odf_del_short_text(GF_ShortTextual *std)
2999 {
3000 if (!std) return GF_BAD_PARAM;
3001
3002 if (std->eventName) gf_free(std->eventName);
3003 if (std->eventText) gf_free(std->eventText);
3004 gf_free(std);
3005 return GF_OK;
3006 }
3007
gf_odf_read_short_text(GF_BitStream * bs,GF_ShortTextual * std,u32 DescSize)3008 GF_Err gf_odf_read_short_text(GF_BitStream *bs, GF_ShortTextual *std, u32 DescSize)
3009 {
3010 GF_Err e;
3011 u32 nbBytes = 0, len;
3012 if (!std) return GF_BAD_PARAM;
3013
3014 std->langCode = gf_bs_read_int(bs, 24);
3015 std->isUTF8 = gf_bs_read_int(bs, 1);
3016 /*aligned = */gf_bs_read_int(bs, 7);
3017 nbBytes += 4;
3018
3019 e = OD_ReadUTF8String(bs, &std->eventName, std->isUTF8, &len);
3020 if (e) return e;
3021 nbBytes += len;
3022 e = OD_ReadUTF8String(bs, &std->eventText, std->isUTF8, &len);
3023 if (e) return e;
3024 nbBytes += len;
3025 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
3026 return GF_OK;
3027 }
3028
gf_odf_size_short_text(GF_ShortTextual * std,u32 * outSize)3029 GF_Err gf_odf_size_short_text(GF_ShortTextual *std, u32 *outSize)
3030 {
3031 if (!std) return GF_BAD_PARAM;
3032 *outSize = 4;
3033 *outSize += OD_SizeUTF8String(std->eventName, std->isUTF8) + OD_SizeUTF8String(std->eventText, std->isUTF8);
3034 return GF_OK;
3035 }
3036
gf_odf_write_short_text(GF_BitStream * bs,GF_ShortTextual * std)3037 GF_Err gf_odf_write_short_text(GF_BitStream *bs, GF_ShortTextual *std)
3038 {
3039 GF_Err e;
3040 u32 size;
3041 if (!std) return GF_BAD_PARAM;
3042
3043 e = gf_odf_size_descriptor((GF_Descriptor *)std, &size);
3044 if (e) return e;
3045 e = gf_odf_write_base_descriptor(bs, std->tag, size);
3046 if (e) return e;
3047 gf_bs_write_int(bs, std->langCode, 24);
3048 gf_bs_write_int(bs, std->isUTF8, 1);
3049 gf_bs_write_int(bs, 0, 7);
3050 OD_WriteUTF8String(bs, std->eventName, std->isUTF8);
3051 OD_WriteUTF8String(bs, std->eventText, std->isUTF8);
3052 return GF_OK;
3053 }
3054
gf_odf_new_smpte_camera()3055 GF_Descriptor *gf_odf_new_smpte_camera()
3056 {
3057 GF_SMPTECamera *newDesc = (GF_SMPTECamera *)gf_malloc(sizeof(GF_SMPTECamera));
3058 if (!newDesc) return NULL;
3059
3060 newDesc->ParamList = gf_list_new();
3061 if (!newDesc->ParamList) {
3062 gf_free(newDesc);
3063 return NULL;
3064 }
3065 newDesc->cameraID = 0;
3066 newDesc->tag = GF_ODF_SMPTE_TAG;
3067 return (GF_Descriptor *)newDesc;
3068 }
3069
gf_odf_del_smpte_camera(GF_SMPTECamera * cpd)3070 GF_Err gf_odf_del_smpte_camera(GF_SMPTECamera *cpd)
3071 {
3072 u32 i;
3073 GF_SmpteParam *tmp;
3074 if (!cpd) return GF_BAD_PARAM;
3075
3076 i = 0;
3077 while ((tmp = (GF_SmpteParam *)gf_list_enum(cpd->ParamList, &i))) {
3078 gf_free(tmp);
3079 }
3080 gf_list_del(cpd->ParamList);
3081 gf_free(cpd);
3082 return GF_OK;
3083 }
gf_odf_read_smpte_camera(GF_BitStream * bs,GF_SMPTECamera * cpd,u32 DescSize)3084 GF_Err gf_odf_read_smpte_camera(GF_BitStream *bs, GF_SMPTECamera *cpd, u32 DescSize)
3085 {
3086 GF_Err e;
3087 u32 nbBytes = 0, i, count;
3088 if (!cpd) return GF_BAD_PARAM;
3089
3090 cpd->cameraID = gf_bs_read_int(bs, 8);
3091 count = gf_bs_read_int(bs, 8);
3092 nbBytes += 2;
3093
3094 for (i = 0; i< count; i++) {
3095 GF_SmpteParam *tmp = (GF_SmpteParam*)gf_malloc(sizeof(GF_SmpteParam));
3096 if (!tmp) return GF_OUT_OF_MEM;
3097 tmp->paramID = gf_bs_read_int(bs, 8);
3098 tmp->param = gf_bs_read_int(bs, 32);
3099 nbBytes += 5;
3100 e = gf_list_add(cpd->ParamList, tmp);
3101 if (e) return e;
3102 }
3103 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
3104 return GF_OK;
3105 }
3106
gf_odf_size_smpte_camera(GF_SMPTECamera * cpd,u32 * outSize)3107 GF_Err gf_odf_size_smpte_camera(GF_SMPTECamera *cpd, u32 *outSize)
3108 {
3109 if (!cpd) return GF_BAD_PARAM;
3110 *outSize = 2 + 5 * gf_list_count(cpd->ParamList);
3111 return GF_OK;
3112 }
3113
gf_odf_write_smpte_camera(GF_BitStream * bs,GF_SMPTECamera * cpd)3114 GF_Err gf_odf_write_smpte_camera(GF_BitStream *bs, GF_SMPTECamera *cpd)
3115 {
3116 GF_Err e;
3117 GF_SmpteParam *tmp;
3118 u32 size, i;
3119 if (!cpd) return GF_BAD_PARAM;
3120
3121 e = gf_odf_size_descriptor((GF_Descriptor *)cpd, &size);
3122 if (e) return e;
3123 e = gf_odf_write_base_descriptor(bs, cpd->tag, size);
3124 if (e) return e;
3125 gf_bs_write_int(bs, cpd->cameraID, 8);
3126 gf_bs_write_int(bs, gf_list_count(cpd->ParamList), 8);
3127
3128 i = 0;
3129 while ((tmp = (GF_SmpteParam *)gf_list_enum(cpd->ParamList, &i))) {
3130 gf_bs_write_int(bs, tmp->paramID, 8);
3131 gf_bs_write_int(bs, tmp->param, 32);
3132 }
3133 return GF_OK;
3134 }
3135
gf_odf_new_sup_cid()3136 GF_Descriptor *gf_odf_new_sup_cid()
3137 {
3138 GF_SCIDesc *newDesc = (GF_SCIDesc *)gf_malloc(sizeof(GF_SCIDesc));
3139 if (!newDesc) return NULL;
3140 newDesc->supplContentIdentifierTitle = NULL;
3141 newDesc->supplContentIdentifierValue = NULL;
3142 newDesc->languageCode = 0;
3143 newDesc->tag = GF_ODF_SCI_TAG;
3144 return (GF_Descriptor *)newDesc;
3145 }
3146
gf_odf_del_sup_cid(GF_SCIDesc * scid)3147 GF_Err gf_odf_del_sup_cid(GF_SCIDesc *scid)
3148 {
3149 if (!scid) return GF_BAD_PARAM;
3150
3151 if (scid->supplContentIdentifierTitle) gf_free(scid->supplContentIdentifierTitle);
3152 if (scid->supplContentIdentifierValue) gf_free(scid->supplContentIdentifierValue);
3153 gf_free(scid);
3154 return GF_OK;
3155 }
3156
gf_odf_read_sup_cid(GF_BitStream * bs,GF_SCIDesc * scid,u32 DescSize)3157 GF_Err gf_odf_read_sup_cid(GF_BitStream *bs, GF_SCIDesc *scid, u32 DescSize)
3158 {
3159 GF_Err e;
3160 u32 nbBytes = 0, len;
3161 if (!scid) return GF_BAD_PARAM;
3162
3163 scid->languageCode = gf_bs_read_int(bs, 24);
3164 nbBytes += 3;
3165 e = OD_ReadUTF8String(bs, &scid->supplContentIdentifierTitle, GF_TRUE, &len);
3166 if (e) return e;
3167 nbBytes += len;
3168 e = OD_ReadUTF8String(bs, &scid->supplContentIdentifierValue, GF_TRUE, &len);
3169 if (e) return e;
3170 nbBytes += len;
3171 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
3172 return GF_OK;
3173 }
3174
3175
gf_odf_size_sup_cid(GF_SCIDesc * scid,u32 * outSize)3176 GF_Err gf_odf_size_sup_cid(GF_SCIDesc *scid, u32 *outSize)
3177 {
3178 if (!scid) return GF_BAD_PARAM;
3179 *outSize = 3 + OD_SizeUTF8String(scid->supplContentIdentifierTitle, GF_TRUE) + OD_SizeUTF8String(scid->supplContentIdentifierValue, GF_TRUE);
3180 return GF_OK;
3181 }
gf_odf_write_sup_cid(GF_BitStream * bs,GF_SCIDesc * scid)3182 GF_Err gf_odf_write_sup_cid(GF_BitStream *bs, GF_SCIDesc *scid)
3183 {
3184 GF_Err e;
3185 u32 size;
3186 if (!scid) return GF_BAD_PARAM;
3187 e = gf_odf_size_descriptor((GF_Descriptor *)scid, &size);
3188 if (e) return e;
3189 e = gf_odf_write_base_descriptor(bs, scid->tag, size);
3190 if (e) return e;
3191 gf_bs_write_int(bs, scid->languageCode, 24);
3192 OD_WriteUTF8String(bs, scid->supplContentIdentifierTitle, GF_TRUE);
3193 OD_WriteUTF8String(bs, scid->supplContentIdentifierValue, GF_TRUE);
3194 return GF_OK;
3195 }
3196
3197
3198 /*IPMPX stuff*/
gf_odf_new_ipmp_tool_list()3199 GF_Descriptor *gf_odf_new_ipmp_tool_list()
3200 {
3201 GF_IPMP_ToolList*newDesc = (GF_IPMP_ToolList*)gf_malloc(sizeof(GF_IPMP_ToolList));
3202 if (!newDesc) return NULL;
3203 newDesc->ipmp_tools = gf_list_new();
3204 newDesc->tag = GF_ODF_IPMP_TL_TAG;
3205 return (GF_Descriptor *)newDesc;
3206 }
3207
gf_odf_del_ipmp_tool_list(GF_IPMP_ToolList * ipmptl)3208 GF_Err gf_odf_del_ipmp_tool_list(GF_IPMP_ToolList *ipmptl)
3209 {
3210 if (!ipmptl) return GF_BAD_PARAM;
3211
3212 while (gf_list_count(ipmptl->ipmp_tools)) {
3213 GF_IPMP_Tool *t = (GF_IPMP_Tool *)gf_list_get(ipmptl->ipmp_tools, 0);
3214 gf_list_rem(ipmptl->ipmp_tools, 0);
3215 if (t->tool_url) gf_free(t->tool_url);
3216 gf_free(t);
3217 }
3218 gf_list_del(ipmptl->ipmp_tools);
3219 gf_free(ipmptl);
3220 return GF_OK;
3221 }
3222
gf_odf_read_ipmp_tool_list(GF_BitStream * bs,GF_IPMP_ToolList * ipmptl,u32 DescSize)3223 GF_Err gf_odf_read_ipmp_tool_list(GF_BitStream *bs, GF_IPMP_ToolList *ipmptl, u32 DescSize)
3224 {
3225 GF_Err e;
3226 u32 tmpSize;
3227 u32 nbBytes = 0;
3228 if (!ipmptl) return GF_BAD_PARAM;
3229
3230 while (nbBytes < DescSize) {
3231 GF_Descriptor *tmp = NULL;
3232 e = gf_odf_parse_descriptor(bs, &tmp, &tmpSize);
3233 if (e) return e;
3234 if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;
3235 e = gf_list_add(ipmptl->ipmp_tools, tmp);
3236 if (e) return e;
3237 nbBytes += tmpSize + gf_odf_size_field_size(tmpSize);
3238 }
3239 if (nbBytes != DescSize) return GF_ODF_INVALID_DESCRIPTOR;
3240 return GF_OK;
3241 }
3242
3243
gf_odf_size_ipmp_tool_list(GF_IPMP_ToolList * ipmptl,u32 * outSize)3244 GF_Err gf_odf_size_ipmp_tool_list(GF_IPMP_ToolList *ipmptl, u32 *outSize)
3245 {
3246 if (!ipmptl) return GF_BAD_PARAM;
3247 *outSize = 0;
3248 return gf_odf_size_descriptor_list(ipmptl->ipmp_tools, outSize);
3249 }
3250
gf_odf_write_ipmp_tool_list(GF_BitStream * bs,GF_IPMP_ToolList * ipmptl)3251 GF_Err gf_odf_write_ipmp_tool_list(GF_BitStream *bs, GF_IPMP_ToolList *ipmptl)
3252 {
3253 GF_Err e;
3254 u32 size;
3255 if (!ipmptl) return GF_BAD_PARAM;
3256 e = gf_odf_size_descriptor((GF_Descriptor *)ipmptl, &size);
3257 if (e) return e;
3258 e = gf_odf_write_base_descriptor(bs, ipmptl->tag, size);
3259 if (e) return e;
3260 return gf_odf_write_descriptor_list(bs, ipmptl->ipmp_tools);
3261 }
3262
gf_odf_new_ipmp_tool()3263 GF_Descriptor *gf_odf_new_ipmp_tool()
3264 {
3265 GF_IPMP_Tool *newDesc = (GF_IPMP_Tool*)gf_malloc(sizeof(GF_IPMP_Tool));
3266 if (!newDesc) return NULL;
3267 memset(newDesc, 0, sizeof(GF_IPMP_Tool));
3268 newDesc->tag = GF_ODF_IPMP_TL_TAG;
3269 return (GF_Descriptor *)newDesc;
3270 }
3271
gf_odf_del_ipmp_tool(GF_IPMP_Tool * ipmpt)3272 GF_Err gf_odf_del_ipmp_tool(GF_IPMP_Tool *ipmpt)
3273 {
3274 if (!ipmpt) return GF_BAD_PARAM;
3275 if (ipmpt->tool_url) gf_free(ipmpt->tool_url);
3276 gf_free(ipmpt);
3277 return GF_OK;
3278 }
3279
gf_odf_read_ipmp_tool(GF_BitStream * bs,GF_IPMP_Tool * ipmpt,u32 DescSize)3280 GF_Err gf_odf_read_ipmp_tool(GF_BitStream *bs, GF_IPMP_Tool *ipmpt, u32 DescSize)
3281 {
3282 Bool is_alt, is_param;
3283 u32 nbBytes = 0;
3284 if (!ipmpt) return GF_BAD_PARAM;
3285 gf_bs_read_data(bs, (char*)ipmpt->IPMP_ToolID, 16);
3286 is_alt = (Bool)gf_bs_read_int(bs, 1);
3287 is_param = (Bool)gf_bs_read_int(bs, 1);
3288 gf_bs_read_int(bs, 6);
3289 nbBytes = 17;
3290
3291 if (is_alt) {
3292 u32 i;
3293 ipmpt->num_alternate = gf_bs_read_int(bs, 8);
3294 nbBytes += 1;
3295 for (i = 0; i<ipmpt->num_alternate; i++) {
3296 gf_bs_read_data(bs, (char*)ipmpt->specificToolID[i], 16);
3297 nbBytes += 16;
3298 if (nbBytes>DescSize) break;
3299 }
3300 }
3301 if (nbBytes>DescSize) return GF_ODF_INVALID_DESCRIPTOR;
3302
3303 if (is_param) {}
3304
3305 if (nbBytes<DescSize) {
3306 u32 s;
3307 nbBytes += gf_ipmpx_array_size(bs, &s);
3308 if (s) {
3309 ipmpt->tool_url = (char*)gf_malloc(sizeof(char)*(s + 1));
3310 gf_bs_read_data(bs, ipmpt->tool_url, s);
3311 ipmpt->tool_url[s] = 0;
3312 nbBytes += s;
3313 }
3314 }
3315
3316 if (nbBytes != DescSize) return GF_NON_COMPLIANT_BITSTREAM;
3317 return GF_OK;
3318 }
3319
3320
gf_odf_size_ipmp_tool(GF_IPMP_Tool * ipmpt,u32 * outSize)3321 GF_Err gf_odf_size_ipmp_tool(GF_IPMP_Tool *ipmpt, u32 *outSize)
3322 {
3323 if (!ipmpt) return GF_BAD_PARAM;
3324 *outSize = 17;
3325 if (ipmpt->num_alternate) *outSize += 1 + 16 * ipmpt->num_alternate;
3326
3327 if (ipmpt->tool_url) {
3328 u32 s = (u32)strlen(ipmpt->tool_url);
3329 *outSize += gf_odf_size_field_size(s) - 1 + s;
3330 }
3331 return GF_OK;
3332 }
3333
gf_odf_write_ipmp_tool(GF_BitStream * bs,GF_IPMP_Tool * ipmpt)3334 GF_Err gf_odf_write_ipmp_tool(GF_BitStream *bs, GF_IPMP_Tool *ipmpt)
3335 {
3336 GF_Err e;
3337 u32 size;
3338 if (!ipmpt) return GF_BAD_PARAM;
3339 e = gf_odf_size_descriptor((GF_Descriptor *)ipmpt, &size);
3340 if (e) return e;
3341 e = gf_odf_write_base_descriptor(bs, ipmpt->tag, size);
3342 if (e) return e;
3343
3344 gf_bs_write_data(bs, (char*)ipmpt->IPMP_ToolID, 16);
3345 gf_bs_write_int(bs, ipmpt->num_alternate ? 1 : 0, 1);
3346 gf_bs_write_int(bs, 0, 1);
3347 gf_bs_write_int(bs, 0, 6);
3348
3349 if (ipmpt->num_alternate) {
3350 u32 i;
3351 gf_bs_write_int(bs, ipmpt->num_alternate, 8);
3352 for (i = 0; i<ipmpt->num_alternate; i++) gf_bs_write_data(bs, (char*)ipmpt->specificToolID[i], 16);
3353 }
3354 if (ipmpt->tool_url) gf_ipmpx_write_array(bs, ipmpt->tool_url, (u32)strlen(ipmpt->tool_url));
3355 return GF_OK;
3356 }
3357
3358 #endif /*GPAC_MINIMAL_ODF*/
3359