GF_Err gf_odf_write_descriptor(GF_BitStream *bs, GF_Descriptor *desc)
{
	switch(desc->tag) {
	case GF_ODF_IOD_TAG :
		return gf_odf_write_iod(bs, (GF_InitialObjectDescriptor *)desc);
	case GF_ODF_ESD_TAG :
		return gf_odf_write_esd(bs, (GF_ESD *)desc);
	case GF_ODF_DCD_TAG :
		return gf_odf_write_dcd(bs, (GF_DecoderConfig *)desc);
	case GF_ODF_SLC_TAG :
		return gf_odf_write_slc(bs, (GF_SLConfig *)desc);
	case GF_ODF_ESD_INC_TAG:
		return gf_odf_write_esd_inc(bs, (GF_ES_ID_Inc *)desc);
	case GF_ODF_ESD_REF_TAG:
		return gf_odf_write_esd_ref(bs, (GF_ES_ID_Ref *)desc);


	case GF_ODF_ISOM_IOD_TAG:
		return gf_odf_write_isom_iod(bs, (GF_IsomInitialObjectDescriptor *)desc);
	case GF_ODF_ISOM_OD_TAG:
		return gf_odf_write_isom_od(bs, (GF_IsomObjectDescriptor *)desc);
	case GF_ODF_OD_TAG:
		return gf_odf_write_od(bs, (GF_ObjectDescriptor *)desc);
	case GF_ODF_SEGMENT_TAG:
		return gf_odf_write_segment(bs, (GF_Segment *) desc);
	case GF_ODF_MUXINFO_TAG:
		return gf_odf_write_muxinfo(bs, (GF_MuxInfo *) desc);

	case GF_ODF_AUX_VIDEO_DATA:
		return gf_odf_write_auxvid(bs, (GF_AuxVideoDescriptor *)desc);

	case GF_ODF_LANG_TAG:
	case GF_ODF_GPAC_LANG:
		return gf_odf_write_lang(bs, (GF_Language *)desc);

#ifndef GPAC_MINIMAL_ODF
	case GF_ODF_MEDIATIME_TAG:
		return gf_odf_write_mediatime(bs, (GF_MediaTime *) desc);
	case GF_ODF_CC_TAG:
		return gf_odf_write_cc(bs, (GF_CCDescriptor *)desc);
	case GF_ODF_CC_DATE_TAG:
		return gf_odf_write_cc_date(bs, (GF_CC_Date *)desc);
	case GF_ODF_CC_NAME_TAG:
		return gf_odf_write_cc_name(bs, (GF_CC_Name *)desc);
	case GF_ODF_CI_TAG:
		return gf_odf_write_ci(bs, (GF_CIDesc *)desc);

	case GF_ODF_TEXT_TAG:
		return gf_odf_write_exp_text(bs, (GF_ExpandedTextual *)desc);
	case GF_ODF_EXT_PL_TAG:
		return gf_odf_write_pl_ext(bs, (GF_PLExt *)desc);
	case GF_ODF_IPI_PTR_TAG:
	case GF_ODF_ISOM_IPI_PTR_TAG:
		return gf_odf_write_ipi_ptr(bs, (GF_IPIPtr *)desc);
	case GF_ODF_IPMP_TAG:
		return gf_odf_write_ipmp(bs, (GF_IPMP_Descriptor *)desc);
	case GF_ODF_IPMP_PTR_TAG:
		return gf_odf_write_ipmp_ptr(bs, (GF_IPMPPtr *)desc);
	case GF_ODF_KW_TAG:
		return gf_odf_write_kw(bs, (GF_KeyWord *)desc);
	case GF_ODF_OCI_DATE_TAG:
		return gf_odf_write_oci_date(bs, (GF_OCI_Data *)desc);
	case GF_ODF_OCI_NAME_TAG:
		return gf_odf_write_oci_name(bs, (GF_OCICreators *)desc);
	case GF_ODF_PL_IDX_TAG:
		return gf_odf_write_pl_idx(bs, (GF_PL_IDX *)desc);
	case GF_ODF_QOS_TAG:
		return gf_odf_write_qos(bs, (GF_QoS_Descriptor *)desc);
	case GF_ODF_RATING_TAG:
		return gf_odf_write_rating(bs, (GF_Rating *)desc);
	case GF_ODF_REG_TAG:
		return gf_odf_write_reg(bs, (GF_Registration *)desc);
	case GF_ODF_SHORT_TEXT_TAG:
		return gf_odf_write_short_text(bs, (GF_ShortTextual *)desc);
	case GF_ODF_SMPTE_TAG:
		return gf_odf_write_smpte_camera(bs, (GF_SMPTECamera *)desc);
	case GF_ODF_SCI_TAG:
		return gf_odf_write_sup_cid(bs, (GF_SCIDesc *)desc);

	case GF_ODF_IPMP_TL_TAG:
		return gf_odf_write_ipmp_tool_list(bs, (GF_IPMP_ToolList *)desc);
	case GF_ODF_IPMP_TOOL_TAG:
		return gf_odf_write_ipmp_tool(bs, (GF_IPMP_Tool *)desc);
#endif /*GPAC_MINIMAL_ODF*/
	default:
		/*don't write out internal descriptors*/
		if ((desc->tag>=GF_ODF_MUXINFO_TAG) && (desc->tag<=GF_ODF_LASER_CFG_TAG))
			return GF_OK;
		return gf_odf_write_default(bs, (GF_DefaultDescriptor *)desc);
	}
	return GF_OK;
}