⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 odf_code.c

📁 一个用于智能手机的多媒体库适合S60 WinCE的跨平台开发库
💻 C
📖 第 1 页 / 共 5 页
字号:
/* *			GPAC - Multimedia Framework C SDK * *			Copyright (c) Jean Le Feuvre 2000-2005  *					All rights reserved * *  This file is part of GPAC / MPEG-4 ObjectDescriptor sub-project * *  GPAC is free software; you can redistribute it and/or modify *  it under the terms of the GNU Lesser General Public License as published by *  the Free Software Foundation; either version 2, or (at your option) *  any later version. *    *  GPAC is distributed in the hope that it will be useful, *  but WITHOUT ANY WARRANTY; without even the implied warranty of *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the *  GNU Lesser General Public License for more details. *    *  You should have received a copy of the GNU Lesser General Public *  License along with this library; see the file COPYING.  If not, write to *  the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  * */#include <gpac/internal/odf_dev.h>#include <gpac/utf.h>#define DATE_CODING_BIT_LEN	40static GFINLINE GF_Err OD_ReadUTF8String(GF_BitStream *bs, char **string, Bool isUTF8, u32 *read){	u32 len;	*read = 1;	len = gf_bs_read_int(bs, 8) + 1;	if (!isUTF8) len *= 2;	(*string) = (char *) malloc(sizeof(char)*len);	if (! (*string) ) return GF_OUT_OF_MEM;	gf_bs_read_data(bs, (*string), len);	*read += len;	return GF_OK;}static GFINLINE u32 OD_SizeUTF8String(char *string, Bool isUTF8){	if (isUTF8) return 1 + strlen(string);	return 1 + 2*gf_utf8_wcslen((const unsigned short *)string);}static GFINLINE void OD_WriteUTF8String(GF_BitStream *bs, char *string, Bool isUTF8){	u32 len;	if (isUTF8) {		len = strlen(string);		gf_bs_write_int(bs, len, 8);		gf_bs_write_data(bs, string, len);	} else {		len = gf_utf8_wcslen((const unsigned short *)string);		gf_bs_write_int(bs, len, 8);		gf_bs_write_data(bs, string, len*2);	}}/*use to parse strings read the length as well - Warning : the alloc is done here !!*/GF_Err gf_odf_read_url_string(GF_BitStream *bs, char **string, u32 *readBytes){	u32 length;	*readBytes = 0;	/*if the string is not NULL, return an error...*/	if (*string != NULL) return GF_BAD_PARAM;	/*the len is always on 8 bits*/	length = gf_bs_read_int(bs, 8);	*readBytes = 1;	/*JLF AMD to MPEG-4 systems :) - This is not conformant at all, just hoping MPEG will accept it soon	since 255bytes URL is a real pain in the neck*/	if (!length) {		length = gf_bs_read_int(bs, 32);		*readBytes += 4;	}	/*we want to use strlen to get rid of "stringLength" => we need an extra 0*/	(*string) = (char *) malloc(length + 1);	if (! string) return GF_OUT_OF_MEM;	gf_bs_read_data(bs, (*string), length);	*readBytes += length;	(*string)[length] = 0;	return GF_OK;}/*writes string*/GF_Err gf_odf_write_url_string(GF_BitStream *bs, char *string){	u32 len;	/*we accept NULL strings now*/	if (!string) {		gf_bs_write_int(bs, 0, 8);		return GF_OK;	}			len = strlen(string);	if (len > 255) {		gf_bs_write_int(bs, 0, 8);		gf_bs_write_int(bs, len, 32);	} else {		gf_bs_write_int(bs, len, 8);	}	gf_bs_write_data(bs, string, len);	return GF_OK;}u32 gf_odf_size_url_string(char *string){	u32 len = strlen(string);	if (len>255) return len+5;	return len+1;}GF_Descriptor *gf_odf_new_esd(){	GF_ESD *newDesc = (GF_ESD *) malloc(sizeof(GF_ESD));	if (!newDesc) return NULL;	memset(newDesc, 0, sizeof(GF_ESD));	newDesc->IPIDataSet = gf_list_new();	newDesc->IPMPDescriptorPointers = gf_list_new();	newDesc->extensionDescriptors = gf_list_new();	newDesc->tag = GF_ODF_ESD_TAG;	return (GF_Descriptor *) newDesc;}GF_Err gf_odf_del_esd(GF_ESD *esd){	GF_Err e;	if (!esd) return GF_BAD_PARAM;	if (esd->URLString)	free(esd->URLString);	if (esd->decoderConfig)	{		e = gf_odf_delete_descriptor((GF_Descriptor *) esd->decoderConfig);		if (e) return e;	}	if (esd->slConfig) {		e = gf_odf_delete_descriptor((GF_Descriptor *) esd->slConfig);		if (e) return e;	}	if (esd->ipiPtr) {		e = gf_odf_delete_descriptor((GF_Descriptor *) esd->ipiPtr);		if (e) return e;	}	if (esd->qos) {		e = gf_odf_delete_descriptor((GF_Descriptor *) esd->qos);		if (e) return e;	}	if (esd->RegDescriptor)	{		e = gf_odf_delete_descriptor((GF_Descriptor *) esd->RegDescriptor);		if (e) return e;	}	if (esd->langDesc)	{		e = gf_odf_delete_descriptor((GF_Descriptor *) esd->langDesc);		if (e) return e;	}	e = gf_odf_delete_descriptor_list(esd->IPIDataSet);	if (e) return e;	e = gf_odf_delete_descriptor_list(esd->IPMPDescriptorPointers);	if (e) return e;	e = gf_odf_delete_descriptor_list(esd->extensionDescriptors);	if (e) return e;	free(esd);	return GF_OK;}GF_Err AddDescriptorToESD(GF_ESD *esd, GF_Descriptor *desc){	if (!esd || !desc) return GF_BAD_PARAM;	switch (desc->tag) {	case GF_ODF_DCD_TAG:		if (esd->decoderConfig) return GF_ODF_INVALID_DESCRIPTOR;		esd->decoderConfig = (GF_DecoderConfig *) desc;		break;	case GF_ODF_SLC_TAG:		if (esd->slConfig) return GF_ODF_INVALID_DESCRIPTOR;		esd->slConfig = (GF_SLConfig *) desc;		break;	//the GF_ODF_ISOM_IPI_PTR_TAG is only used in the file format and replaces GF_ODF_IPI_PTR_TAG...	case GF_ODF_ISOM_IPI_PTR_TAG:	case GF_ODF_IPI_PTR_TAG:		if (esd->ipiPtr) return GF_ODF_INVALID_DESCRIPTOR;		esd->ipiPtr = (GF_IPIPtr *) desc;		break;	case GF_ODF_QOS_TAG:		if (esd->qos) return GF_ODF_INVALID_DESCRIPTOR;		esd->qos  =(GF_QoS_Descriptor *) desc;		break;	case GF_ODF_LANG_TAG:		if (esd->langDesc) return GF_ODF_INVALID_DESCRIPTOR;		esd->langDesc = (GF_Language *) desc;		break;	case GF_ODF_CI_TAG:	case GF_ODF_SCI_TAG:		return gf_list_add(esd->IPIDataSet, desc);	//we use the same struct for v1 and v2 IPMP DPs	case GF_ODF_IPMP_PTR_TAG:		return gf_list_add(esd->IPMPDescriptorPointers, desc);	case GF_ODF_REG_TAG:		if (esd->RegDescriptor) return GF_ODF_INVALID_DESCRIPTOR;		esd->RegDescriptor =(GF_Registration *) desc;		break;	case GF_ODF_MUXINFO_TAG:		gf_list_add(esd->extensionDescriptors, desc);		break;	default:		if ( (desc->tag >= GF_ODF_EXT_BEGIN_TAG) &&			(desc->tag <= GF_ODF_EXT_END_TAG) ) {			return gf_list_add(esd->extensionDescriptors, desc);		}		gf_odf_delete_descriptor(desc);		return GF_OK;	}	return GF_OK;}GF_Err gf_odf_read_esd(GF_BitStream *bs, GF_ESD *esd, u32 DescSize){	GF_Err e = GF_OK;	u32 ocrflag, urlflag, streamdependflag, tmp_size, nbBytes, read;	if (! esd) return GF_BAD_PARAM;	nbBytes = 0;	esd->ESID = gf_bs_read_int(bs, 16);	streamdependflag = gf_bs_read_int(bs, 1);	urlflag = gf_bs_read_int(bs, 1);	ocrflag = gf_bs_read_int(bs, 1);	esd->streamPriority = gf_bs_read_int(bs, 5);	nbBytes += 3;		if (streamdependflag) {		esd->dependsOnESID = gf_bs_read_int(bs, 16);		nbBytes += 2;	}	if (urlflag) {		e = gf_odf_read_url_string(bs, & esd->URLString, &read);		if (e) return e;		nbBytes += read;	}	if (ocrflag) {		esd->OCRESID = gf_bs_read_int(bs, 16);		nbBytes += 2;	}	/*fix broken sync*///	if (esd->OCRESID == esd->ESID) esd->OCRESID = 0;	while (nbBytes < DescSize) {		GF_Descriptor *tmp = NULL;		e = gf_odf_parse_descriptor(bs, &tmp, &tmp_size);		/*fix for iPod files*/		if (e==GF_ODF_INVALID_DESCRIPTOR) {			nbBytes += tmp_size;			if (nbBytes>DescSize) return e;			gf_bs_read_int(bs, DescSize-nbBytes);			return GF_OK;		}		if (e) return e;		if (!tmp) return GF_ODF_INVALID_DESCRIPTOR;		e = AddDescriptorToESD(esd, tmp);		if (e) return e;		nbBytes += tmp_size + gf_odf_size_field_size(tmp_size);				//apple fix		if (!tmp_size) nbBytes = DescSize;	}	if (DescSize != nbBytes) return GF_ODF_INVALID_DESCRIPTOR;	return e;}GF_Err gf_odf_size_esd(GF_ESD *esd, u32 *outSize){	GF_Err e;	u32 tmpSize;	if (! esd) return GF_BAD_PARAM;	*outSize = 0;	*outSize += 3;	/*this helps keeping proper sync: some people argue that OCR_ES_ID == ES_ID is a circular reference	of streams. Since this is equivalent to no OCR_ES_ID, keep it that way*///	if (esd->OCRESID == esd->ESID) esd->OCRESID = 0;	if (esd->dependsOnESID) *outSize += 2;	if (esd->URLString) *outSize += gf_odf_size_url_string(esd->URLString);	if (esd->OCRESID) *outSize += 2;	if (esd->decoderConfig) {		e = gf_odf_size_descriptor((GF_Descriptor *) esd->decoderConfig, &tmpSize);		if (e) return e;		*outSize += tmpSize + gf_odf_size_field_size(tmpSize);	}	if (esd->slConfig) {		e = gf_odf_size_descriptor((GF_Descriptor *) esd->slConfig, &tmpSize);		if (e) return e;		*outSize += tmpSize + gf_odf_size_field_size(tmpSize);	}	if (esd->ipiPtr) {		e = gf_odf_size_descriptor((GF_Descriptor *) esd->ipiPtr, &tmpSize);			if (e) return e;		*outSize += tmpSize + gf_odf_size_field_size(tmpSize);	}	if (esd->langDesc) {		e = gf_odf_size_descriptor((GF_Descriptor *) esd->langDesc, &tmpSize);			if (e) return e;		*outSize += tmpSize + gf_odf_size_field_size(tmpSize);	}	e = gf_odf_size_descriptor_list(esd->IPIDataSet, outSize);	if (e) return e;	e = gf_odf_size_descriptor_list(esd->IPMPDescriptorPointers, outSize);	if (e) return e;	if (esd->qos) {		e = gf_odf_size_descriptor((GF_Descriptor *) esd->qos, &tmpSize);			if (e) return e;		*outSize += tmpSize + gf_odf_size_field_size(tmpSize);	}	if (esd->RegDescriptor) {		e = gf_odf_size_descriptor((GF_Descriptor *) esd->RegDescriptor, &tmpSize);			if (e) return e;		*outSize += tmpSize + gf_odf_size_field_size(tmpSize);	}	return gf_odf_size_descriptor_list(esd->extensionDescriptors, outSize);}GF_Err gf_odf_write_esd(GF_BitStream *bs, GF_ESD *esd){	GF_Err e;	u32 size;	if (! esd) return GF_BAD_PARAM;	e = gf_odf_size_descriptor((GF_Descriptor *)esd, &size);	if (e) return e;	e = gf_odf_write_base_descriptor(bs, esd->tag, size);	if (e) return e;	gf_bs_write_int(bs, esd->ESID, 16);	gf_bs_write_int(bs, esd->dependsOnESID ? 1 : 0, 1);	gf_bs_write_int(bs, esd->URLString != NULL ? 1 : 0, 1);	gf_bs_write_int(bs, esd->OCRESID ? 1 : 0, 1);	gf_bs_write_int(bs, esd->streamPriority, 5);	if (esd->dependsOnESID) {		gf_bs_write_int(bs, esd->dependsOnESID, 16);	}	if (esd->URLString) {		e = gf_odf_write_url_string(bs, esd->URLString);		if (e) return e;	}	if (esd->OCRESID) {		gf_bs_write_int(bs, esd->OCRESID, 16);	}	if (esd->decoderConfig) {		e = gf_odf_write_descriptor(bs, (GF_Descriptor *) esd->decoderConfig);		if (e) return e;	}	if (esd->slConfig) {		e = gf_odf_write_descriptor(bs, (GF_Descriptor *) esd->slConfig);		if (e) return e;	}	if (esd->ipiPtr) {		e = gf_odf_write_descriptor(bs, (GF_Descriptor *) esd->ipiPtr);		if (e) return e;	}	if (esd->langDesc) {		e = gf_odf_write_descriptor(bs, (GF_Descriptor *) esd->langDesc);		if (e) return e;	}	e = gf_odf_write_descriptor_list(bs, esd->IPIDataSet);	if (e) return e;	e = gf_odf_write_descriptor_list(bs, esd->IPMPDescriptorPointers);	if (e) return e;	if (esd->qos) {		e = gf_odf_write_descriptor(bs, (GF_Descriptor *) esd->qos);		if (e) return e;	}	if (esd->RegDescriptor) {		e = gf_odf_write_descriptor(bs, (GF_Descriptor *) esd->RegDescriptor);		if (e) return e;	}	return gf_odf_write_descriptor_list(bs, esd->extensionDescriptors);}GF_Descriptor *gf_odf_new_iod(){	GF_InitialObjectDescriptor *newDesc = (GF_InitialObjectDescriptor *) malloc(sizeof(GF_InitialObjectDescriptor));	if (!newDesc) return NULL;	memset(newDesc, 0, sizeof(GF_InitialObjectDescriptor));	newDesc->ESDescriptors = gf_list_new();	newDesc->OCIDescriptors = gf_list_new();	newDesc->IPMP_Descriptors = gf_list_new();	newDesc->extensionDescriptors = gf_list_new();	newDesc->tag = GF_ODF_IOD_TAG;	return (GF_Descriptor *) newDesc;}GF_Err gf_odf_del_iod(GF_InitialObjectDescriptor *iod){	GF_Err e;	if (!iod) return GF_BAD_PARAM;	if (iod->URLString)	free(iod->URLString);	e = gf_odf_delete_descriptor_list(iod->ESDescriptors);	if (e) return e;	e = gf_odf_delete_descriptor_list(iod->OCIDescriptors);	if (e) return e;	e = gf_odf_delete_descriptor_list(iod->IPMP_Descriptors);	if (e) return e;	e = gf_odf_delete_descriptor_list(iod->extensionDescriptors);	if (e) return e;	if (iod->IPMPToolList) gf_odf_delete_descriptor((GF_Descriptor *) iod->IPMPToolList);	free(iod);	return GF_OK;}GF_Err AddDescriptorToIOD(GF_InitialObjectDescriptor *iod, GF_Descriptor *desc){	if (!iod || !desc) return GF_BAD_PARAM;	switch (desc->tag) {	case GF_ODF_ESD_TAG:		return gf_list_add(iod->ESDescriptors, desc);	//we use the same struct for v1 and v2 IPMP DPs	case GF_ODF_IPMP_PTR_TAG:	/*IPMPX*/	case GF_ODF_IPMP_TAG:		return gf_list_add(iod->IPMP_Descriptors, desc);		/*IPMPX*/	case GF_ODF_IPMP_TL_TAG:		if (iod->IPMPToolList) gf_odf_desc_del((GF_Descriptor *)iod->IPMPToolList);		iod->IPMPToolList = (GF_IPMP_ToolList *)desc;		return GF_OK;	default:		break;	}	if ( (desc->tag >= GF_ODF_OCI_BEGIN_TAG) && (desc->tag <= GF_ODF_OCI_END_TAG) ) return gf_list_add(iod->OCIDescriptors, desc);	if ( (desc->tag >= GF_ODF_EXT_BEGIN_TAG) && (desc->tag <= GF_ODF_EXT_END_TAG) ) return gf_list_add(iod->extensionDescriptors, desc);	return GF_BAD_PARAM;}GF_Err gf_odf_read_iod(GF_BitStream *bs, GF_InitialObjectDescriptor *iod, u32 DescSize){	GF_Err e;	u32 reserved, urlflag, read;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -