Mercurial > pt1.oyama
view libdlna-0.2.3/src/av_mpeg4_part2.c @ 130:cc3e3f370aec
tune for streaming.
author | Naoya OYAMA <naoya.oyama@gmail.com> |
---|---|
date | Sun, 10 Oct 2010 22:44:28 +0900 |
parents | 4f6d9621ee00 |
children |
line wrap: on
line source
/* * libdlna: reference DLNA standards implementation. * Copyright (C) 2007 Benjamin Zores <ben@geexbox.org> * * This file is part of libdlna. * * libdlna 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.1 of the License, or (at your option) any later version. * * libdlna 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 libdlna; if not, write to the Free Software * Foundation, Inc, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #include <stdlib.h> #include <string.h> #include <unistd.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <ffmpeg/avcodec.h> #include "dlna_internals.h" #include "profiles.h" #include "containers.h" typedef enum { MPEG4_VCODEC_INVALID, MPEG4_VCODEC_H263, MPEG4_VCODEC_P2, } mpeg4_vcodec_type_t; static const struct { int codec_id; mpeg4_vcodec_type_t type; } avf_vcodec_mapping[] = { { CODEC_ID_H263, MPEG4_VCODEC_H263 }, { CODEC_ID_H263I, MPEG4_VCODEC_H263 }, { CODEC_ID_H263P, MPEG4_VCODEC_H263 }, { CODEC_ID_MPEG4, MPEG4_VCODEC_P2 }, { CODEC_ID_MSMPEG4V1, MPEG4_VCODEC_P2 }, { CODEC_ID_MSMPEG4V2, MPEG4_VCODEC_P2 }, { CODEC_ID_MSMPEG4V3, MPEG4_VCODEC_P2 }, { -1, 0 } }; typedef enum { MPEG4_VIDEO_PROFILE_INVALID, MPEG4_VIDEO_PROFILE_H263, MPEG4_VIDEO_PROFILE_P2_SP_L0B, MPEG4_VIDEO_PROFILE_P2_SP_L2, MPEG4_VIDEO_PROFILE_P2_SP_L3, MPEG4_VIDEO_PROFILE_P2_SP_L3_VGA, MPEG4_VIDEO_PROFILE_P2_ASP_L4, MPEG4_VIDEO_PROFILE_P2_ASP_L5 } mpeg4_video_profile_t; typedef struct video_properties_s { int width; int height; int fps_num; int fps_den; } video_properties_t; /* H263 Resolutions (all <= 15 fps) */ static video_properties_t profile_h263_res[] = { { 176, 144, 15, 1 }, /* QCIF */ { 128, 96, 15, 1 } /* SQCIF */ }; /* MPEG-4 SP L0B Resolutions (all <= 15 fps) */ static video_properties_t profile_p2_sp_l0b_res[] = { { 176, 144, 15, 1 }, /* QCIF */ { 128, 96, 15, 1 } /* SQCIF */ }; /* MPEG-4 SP L2 Resolutions */ static video_properties_t profile_p2_sp_l2_res[] = { { 352, 288, 15, 1 }, /* CIF */ { 320, 240, 15, 1 }, /* QVGA 4:3 */ { 320, 180, 15, 1 }, /* QVGA 16:9 */ { 176, 144, 30, 1 }, /* QCIF */ { 128, 96, 30, 1 } /* SQCIF */ }; /* MPEG-4 SP L3_VGA Resolutions */ static video_properties_t profile_p2_sp_l3_vga_res[] = { { 640, 480, 30, 1 }, /* VGA */ { 640, 360, 30, 1 } /* VGA 16:9 */ }; /* MPEG-4 L3 / CO Resolutions (all <= 30 fps) */ static video_properties_t profile_p2_sp_l3_co_res[] = { { 352, 288, 30, 1 }, /* CIF, 625SIF */ { 352, 240, 30, 1 }, /* 525SIF */ { 320, 240, 30, 1 }, /* QVGA 4:3 */ { 320, 180, 30, 1 }, /* QVGA 16:9 */ { 240, 180, 30, 1 }, /* 1/7 VGA 4:3 */ { 208, 160, 30, 1 }, /* 1/9 VGA 4:3 */ { 176, 144, 30, 1 }, /* QCIF,625QCIF */ { 176, 120, 30, 1 }, /* 525QCIF */ { 160, 120, 30, 1 }, /* SQVGA 4:3 */ { 160, 112, 30, 1 }, /* 1/16 VGA 4:3 */ { 160, 90, 30, 1 }, /* SQVGA 16:9 */ { 128, 96, 30, 1 } /* SQCIF */ }; /* MPEG-4 ASP L4 SO Resolutions (all <= 30 fps) */ static video_properties_t profile_p2_asp_l4_res[] = { { 352, 576, 30, 1 }, /* 625 1/2 D1 */ { 352, 480, 30, 1 }, /* 525 1/2 D1 */ { 352, 288, 30, 1 }, /* CIF, 625SIF */ { 352, 240, 30, 1 }, /* 525SIF */ { 320, 240, 30, 1 }, /* QVGA 4:3 */ { 320, 180, 30, 1 }, /* QVGA 16:9 */ { 240, 180, 30, 1 }, /* 1/7 VGA 4:3 */ { 208, 160, 30, 1 }, /* 1/9 VGA 4:3 */ { 176, 144, 30, 1 }, /* QCIF,625QCIF */ { 176, 120, 30, 1 }, /* 525QCIF */ { 160, 120, 30, 1 }, /* SQVGA 4:3 */ { 160, 112, 30, 1 }, /* 1/16 VGA 4:3 */ { 160, 90, 30, 1 }, /* SQVGA 16:9 */ { 128, 96, 30, 1 } /* SQCIF */ }; /* MPEG-4 ASP L5 Resolutions (all <= 30 fps) */ static video_properties_t profile_p2_asp_l5_res[] = { { 720, 576, 30, 1 }, /* 625 D1 */ { 720, 480, 30, 1 }, /* 525 D1 */ { 704, 576, 30, 1 }, /* 625 4SIF */ { 704, 480, 30, 1 }, /* 525 4SIF */ { 640, 480, 30, 1 }, /* VGA */ { 640, 360, 30, 1 }, /* VGA 16:9 */ { 544, 576, 30, 1 }, /* 625 3/4 D1 */ { 544, 480, 30, 1 }, /* 525 3/4 D1 */ { 480, 576, 30, 1 }, /* 625 2/3 D1 */ { 480, 480, 30, 1 }, /* 525 2/3 D1 */ { 480, 360, 30, 1 }, /* 9/16 VGA 4:3 */ { 480, 270, 30, 1 }, /* 9/16 VGA 16:9 */ { 352, 576, 30, 1 }, /* 625 1/2 D1 */ { 352, 480, 30, 1 }, /* 525 1/2 D1 */ { 352, 288, 30, 1 }, /* CIF, 625SIF */ { 352, 240, 30, 1 }, /* 525SIF */ { 320, 240, 30, 1 }, /* QVGA 4:3 */ { 320, 180, 30, 1 }, /* QVGA 16:9 */ { 240, 180, 30, 1 }, /* 1/7 VGA 4:3 */ { 208, 160, 30, 1 }, /* 1/9 VGA 4:3 */ { 176, 144, 30, 1 }, /* QCIF,625QCIF */ { 176, 120, 30, 1 }, /* 525QCIF */ { 160, 120, 30, 1 }, /* SQVGA 4:3 */ { 160, 112, 30, 1 }, /* 1/16 VGA 4:3 */ { 160, 90, 30, 1 }, /* SQVGA 16:9 */ { 128, 96, 30, 1 } /* SQCIF */ }; /********************/ /* MPEG-4 Container */ /********************/ /* Profile for MPEG-4 Part 2 Simple Profile with AAC LC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_aac = { .id = "MPEG4_P2_MP4_SP_AAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with HE AAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_heaac = { .id = "MPEG4_P2_MP4_SP_HEAAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with ATRAC3plus audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_atrac3plus = { .id = "MPEG4_P2_MP4_SP_ATRAC3plus", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with AAC LTP audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_aac_ltp = { .id = "MPEG4_P2_MP4_SP_AAC_LTP", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile Level 2 with AAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_l2_aac = { .id = "MPEG4_P2_MP4_SP_L2_AAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF15 }; /* Profile for MPEG-4 Part 2 Simple Profile Level 2 with AMR audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_l2_amr = { .id = "MPEG4_P2_MP4_SP_L2_AMR", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF15 }; /* Profile for MPEG-4 Part 2 Simple Profile Level 3+ with AAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_vga_aac = { .id = "MPEG4_P2_MP4_SP_VGA_AAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Simple Profile Level 3+ with HEAAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_sp_vga_heaac = { .id = "MPEG4_P2_MP4_SP_VGA_HEAAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AAC LC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_aac = { .id = "MPEG4_P2_MP4_ASP_AAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with HEAAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_heaac = { .id = "MPEG4_P2_MP4_ASP_HEAAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with HEAAC multi-channel audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_heaac_mult5 = { .id = "MPEG4_P2_MP4_ASP_HEAAC_MULT5", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with ATRAC3plus audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_actrac3plus = { .id = "MPEG4_P2_MP4_ASP_ATRAC3plus", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 5 with only Simple Object with AAC LC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_l5_so_aac = { .id = "MPEG4_P2_MP4_ASP_L5_SO_AAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 5 with only Simple Object with HEAAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_l5_so_heaac = { .id = "MPEG4_P2_MP4_ASP_L5_SO_HEAAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 5 with only Simple Object with HEAAC multichannel audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_l5_so_heaac_mult5 = { .id = "MPEG4_P2_MP4_ASP_L5_SO_HEAAC_MULT5", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 4 with only Simple Object with AAC LC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_l4_so_aac = { .id = "MPEG4_P2_MP4_ASP_L4_SO_AAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 4 with only Simple Object with HEAAC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_l4_so_heaac = { .id = "MPEG4_P2_MP4_ASP_L4_SO_HEAAC", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 4 with only Simple Object with HEAAC multichannel audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_p2_mp4_asp_l4_so_heaac_mult5 = { .id = "MPEG4_P2_MP4_ASP_L4_SO_HEAAC_MULT5", .mime = MIME_VIDEO_MPEG_4, .label = LABEL_VIDEO_CIF30 }; /* Profile for H263 Profile 0 Level 10 with AAC LC audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_h263_mp4_p0_l10_aac = { .id = "MPEG4_H263_MP4_P0_L10_AAC", .mime = MIME_VIDEO_3GP, .label = LABEL_VIDEO_QCIF15 }; /* Profile for H263 Profile 0 Level 10 with AAC LTP audio, encapsulated in MP4 */ static dlna_profile_t mpeg4_h263_mp4_p0_l10_aac_ltp = { .id = "MPEG4_H263_MP4_P0_L10_AAC_LTP", .mime = MIME_VIDEO_3GP, .label = LABEL_VIDEO_QCIF15 }; /*********************/ /* MPEG-TS Container */ /*********************/ /* Profile for MPEG-4 Part 2 Simple Profile with AAC LC audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_aac = { .id = "MPEG4_P2_TS_SP_AAC", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with AAC LC audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_aac_t = { .id = "MPEG4_P2_TS_SP_AAC_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with AAC LC audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_aac_iso = { .id = "MPEG4_P2_TS_SP_AAC_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with MPEG-1 Layer3 audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_mpeg1_l3 = { .id = "MPEG4_P2_TS_SP_MPEG1_L3", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with MPEG-1 Layer3 audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_mpeg1_l3_t = { .id = "MPEG4_P2_TS_SP_MPEG1_L3_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with MPEG-1 Layer3 audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_mpeg1_l3_iso = { .id = "MPEG4_P2_TS_SP_MPEG1_L3_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with AC3 multichannel audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_ac3 = { .id = "MPEG4_P2_TS_SP_AC3_L3", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with AC3 multichannel audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_ac3_t = { .id = "MPEG4_P2_TS_SP_AC3_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with AC3 multichannel audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_ac3_iso = { .id = "MPEG4_P2_TS_SP_AC3_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with MPEG-1/2 Layer 1/2 multichannel audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_mpeg2_l2 = { .id = "MPEG4_P2_TS_SP_MPEG2_L2", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with MPEG-1/2 Layer1/2 multichannel audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_mpeg2_l2_t = { .id = "MPEG4_P2_TS_SP_MPEG2_L2_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Simple Profile with MPEG-1/2 Layer1/2 multichannel audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_sp_mpeg2_l2_iso = { .id = "MPEG4_P2_TS_SP_MPEG2_L2_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AAC LC audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_aac = { .id = "MPEG4_P2_TS_ASP_AAC", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AAC LC audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_aac_t = { .id = "MPEG4_P2_TS_ASP_AAC_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AAC LC audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_aac_iso = { .id = "MPEG4_P2_TS_ASP_AAC_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with MPEG-1 Layer3 audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_mpeg1_l3 = { .id = "MPEG4_P2_TS_ASP_MPEG1_L3", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with MPEG-1 Layer3 audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_mpeg1_l3_t = { .id = "MPEG4_P2_TS_ASP_MPEG1_L3_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with MPEG-1 Layer3 audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_mpeg1_l3_iso = { .id = "MPEG4_P2_TS_ASP_MPEG1_L3_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AC3 multichannel audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_ac3 = { .id = "MPEG4_P2_TS_ASP_AC3_L3", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AC3 multichannel audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_ac3_t = { .id = "MPEG4_P2_TS_ASP_AC3_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile with AC3 multichannel audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_asp_ac3_iso = { .id = "MPEG4_P2_TS_ASP_AC3_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Core Profile with AC3 multichannel audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_co_ac3 = { .id = "MPEG4_P2_TS_CO_AC3", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Core Profile with AC3 multichannel audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_co_ac3_t = { .id = "MPEG4_P2_TS_CO_AC3_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Core Profile with AC3 multichannel audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_co_ac3_iso = { .id = "MPEG4_P2_TS_CO_AC3_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Core Profile with MPEG-1/2 Layer1/2 audio, encapsulated in MPEG2-TS with a zero timestamp field */ static dlna_profile_t mpeg4_p2_ts_co_mpeg2_l2 = { .id = "MPEG4_P2_TS_CO_MPEG2_L2", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Core Profile with MPEG-1/2 Layer1/2 audio, encapsulated in MPEG2-TS with a valid timestamp field */ static dlna_profile_t mpeg4_p2_ts_co_mpeg2_l2_t = { .id = "MPEG4_P2_TS_CO_MPEG2_L2_T", .mime = MIME_VIDEO_MPEG_TS, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Core Profile with MPEG-1/2 Layer1/2 audio, encapsulated in MPEG2-TS without a timestamp field */ static dlna_profile_t mpeg4_p2_ts_co_mpeg2_l2_iso = { .id = "MPEG4_P2_TS_CO_MPEG2_L2_ISO", .mime = MIME_VIDEO_MPEG, .label = LABEL_VIDEO_CIF30 }; /*****************/ /* ASF Container */ /*****************/ /* Profile for MPEG-4 Part 2 Simple Profile with G.726 audio, encapsulated in ASF */ static dlna_profile_t mpeg4_p2_asf_sp_g726 = { .id = "MPEG4_P2_ASF_SP_G726", .mime = MIME_VIDEO_ASF, .label = LABEL_VIDEO_CIF30 }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 5 with only Simple Object with G.726 audio, encapsulated in ASF */ static dlna_profile_t mpeg4_p2_asf_asp_l5_so_g726 = { .id = "MPEG4_P2_ASF_ASP_L5_SO_G726", .mime = MIME_VIDEO_ASF, .label = LABEL_VIDEO_SD }; /* Profile for MPEG-4 Part 2 Advanced Simple Profile up to Level 4 with only Simple Object with G.726 audio, encapsulated in ASF */ static dlna_profile_t mpeg4_p2_asf_asp_l4_so_g726 = { .id = "MPEG4_P2_ASF_ASP_L4_SO_G726", .mime = MIME_VIDEO_ASF, .label = LABEL_VIDEO_CIF30 }; /******************/ /* 3GPP Container */ /******************/ /* Profile for H.263 Profile 0 Level 10 with AMR-WB+ audio, encapsulated in 3GPP */ static dlna_profile_t mpeg4_h263_3gpp_p0_l10_amr_wbplus = { .id = "MPEG4_H263_3GPP_P0_L10_AMR_WBplus", .mime = MIME_VIDEO_3GP, .label = LABEL_VIDEO_QCIF15 }; /* Profile for MPEG-4 Part 2 Simple Profile Level 0b with AAC audio, encapsulated in 3GPP */ static dlna_profile_t mpeg4_p2_3gpp_sp_l0b_aac = { .id = "MPEG4_P2_3GPP_SP_L0B_AAC", .mime = MIME_VIDEO_3GP, .label = LABEL_VIDEO_QCIF15 }; /* Profile for MPEG-4 Part 2 Simple Profile Level 0b with AMR audio, encapsulated in 3GPP */ static dlna_profile_t mpeg4_p2_3gpp_sp_l0b_amr = { .id = "MPEG4_P2_3GPP_SP_L0B_AMR", .mime = MIME_VIDEO_3GP, .label = LABEL_VIDEO_QCIF15 }; /* Profile for MPEG-4 H.263 Profile 3 Level 10 with AMR audio, encapsulated in 3GPP */ static dlna_profile_t mpeg4_h263_3gpp_p3_l10_amr = { .id = "MPEG4_H263_3GPP_P3_L10_AMR", .mime = MIME_VIDEO_3GP, .label = LABEL_VIDEO_QCIF15 }; static const struct { dlna_profile_t *profile; dlna_container_type_t st; mpeg4_video_profile_t vp; audio_profile_t ap; } mpeg4_profiles_mapping[] = { /* MPEG-4 Container */ { &mpeg4_p2_mp4_sp_aac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AAC }, { &mpeg4_p2_mp4_sp_heaac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AAC_HE_L2 }, { &mpeg4_p2_mp4_sp_atrac3plus, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_ATRAC }, { &mpeg4_p2_mp4_sp_aac_ltp, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AAC_LTP }, { &mpeg4_p2_mp4_sp_l2_aac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L2, AUDIO_PROFILE_AAC }, { &mpeg4_p2_mp4_sp_l2_amr, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L2, AUDIO_PROFILE_AMR }, { &mpeg4_p2_mp4_sp_vga_aac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L3_VGA, AUDIO_PROFILE_AAC }, { &mpeg4_p2_mp4_sp_vga_heaac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_SP_L3_VGA, AUDIO_PROFILE_AAC_HE_L2 }, { &mpeg4_p2_mp4_asp_aac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC }, { &mpeg4_p2_mp4_asp_heaac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC_HE_L2 }, { &mpeg4_p2_mp4_asp_heaac_mult5, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC_HE_MULT5 }, { &mpeg4_p2_mp4_asp_actrac3plus, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_ATRAC }, { &mpeg4_p2_mp4_asp_l5_so_aac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC }, { &mpeg4_p2_mp4_asp_l5_so_heaac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC_HE_L2 }, { &mpeg4_p2_mp4_asp_l5_so_heaac_mult5, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC_HE_MULT5 }, { &mpeg4_p2_mp4_asp_l4_so_aac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_AAC }, { &mpeg4_p2_mp4_asp_l4_so_heaac, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_AAC_HE_L2 }, { &mpeg4_p2_mp4_asp_l4_so_heaac_mult5, CT_MP4, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_AAC_HE_MULT5 }, { &mpeg4_h263_mp4_p0_l10_aac, CT_MP4, MPEG4_VIDEO_PROFILE_H263, AUDIO_PROFILE_AAC }, { &mpeg4_h263_mp4_p0_l10_aac_ltp, CT_MP4, MPEG4_VIDEO_PROFILE_H263, AUDIO_PROFILE_AAC_LTP }, /* MPEG-TS Container */ { &mpeg4_p2_ts_sp_aac, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AAC }, { &mpeg4_p2_ts_sp_aac_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AAC }, { &mpeg4_p2_ts_sp_aac_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AAC }, { &mpeg4_p2_ts_sp_mpeg1_l3, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_MP3 }, { &mpeg4_p2_ts_sp_mpeg1_l3_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_MP3 }, { &mpeg4_p2_ts_sp_mpeg1_l3_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_MP3 }, { &mpeg4_p2_ts_sp_ac3, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_sp_ac3_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_sp_ac3_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_sp_mpeg2_l2, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_MP2 }, { &mpeg4_p2_ts_sp_mpeg2_l2_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_MP2 }, { &mpeg4_p2_ts_sp_mpeg2_l2_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_MP2 }, { &mpeg4_p2_ts_asp_aac, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC }, { &mpeg4_p2_ts_asp_aac_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC }, { &mpeg4_p2_ts_asp_aac_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AAC }, { &mpeg4_p2_ts_asp_mpeg1_l3, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_MP3 }, { &mpeg4_p2_ts_asp_mpeg1_l3_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_MP3 }, { &mpeg4_p2_ts_asp_mpeg1_l3_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_MP3 }, { &mpeg4_p2_ts_asp_ac3, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_asp_ac3_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_asp_ac3_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_co_ac3, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_co_ac3_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_co_ac3_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_AC3 }, { &mpeg4_p2_ts_co_mpeg2_l2, CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_MP2 }, { &mpeg4_p2_ts_co_mpeg2_l2_t, CT_MPEG_TRANSPORT_STREAM_DLNA, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_MP2 }, { &mpeg4_p2_ts_co_mpeg2_l2_iso, CT_MPEG_TRANSPORT_STREAM, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_MP2 }, /* ASF Container */ { &mpeg4_p2_asf_sp_g726, CT_ASF, MPEG4_VIDEO_PROFILE_P2_SP_L3, AUDIO_PROFILE_G726 }, { &mpeg4_p2_asf_asp_l5_so_g726, CT_ASF, MPEG4_VIDEO_PROFILE_P2_ASP_L5, AUDIO_PROFILE_G726 }, { &mpeg4_p2_asf_asp_l4_so_g726, CT_ASF, MPEG4_VIDEO_PROFILE_P2_ASP_L4, AUDIO_PROFILE_G726 }, /* 3GPP Container */ { &mpeg4_h263_3gpp_p0_l10_amr_wbplus, CT_3GP, MPEG4_VIDEO_PROFILE_H263, AUDIO_PROFILE_AMR_WB }, { &mpeg4_p2_3gpp_sp_l0b_aac, CT_3GP, MPEG4_VIDEO_PROFILE_P2_SP_L0B, AUDIO_PROFILE_AAC }, { &mpeg4_p2_3gpp_sp_l0b_amr, CT_3GP, MPEG4_VIDEO_PROFILE_P2_SP_L0B, AUDIO_PROFILE_AMR }, { &mpeg4_h263_3gpp_p3_l10_amr, CT_3GP, MPEG4_VIDEO_PROFILE_H263, AUDIO_PROFILE_AMR }, { NULL, 0, 0, 0 } }; static mpeg4_vcodec_type_t mpeg4_get_vcodec (AVCodecContext *vc) { int i; if (!vc) return MPEG4_VCODEC_INVALID; for (i = 0; avf_vcodec_mapping[i].codec_id != -1; i++) if (vc->codec_id == (unsigned int) avf_vcodec_mapping[i].codec_id) return avf_vcodec_mapping[i].type; return MPEG4_VCODEC_INVALID; } static inline int is_valid_video_profile (video_properties_t res[], int size, AVStream *vs, AVCodecContext *vc) { int i; for (i = 0; i < size / (int) sizeof (video_properties_t); i++) { if (res[i].width == vc->width && res[i].height == vc->height && (vs->r_frame_rate.num / vs->r_frame_rate.num) <= (res[i].fps_num / res[i].fps_den)) return 1; } return 0; } static mpeg4_video_profile_t mpeg4_video_get_profile (mpeg4_vcodec_type_t vctype, AVStream *vs, AVCodecContext *vc) { if (!vs || !vc) return MPEG4_VIDEO_PROFILE_INVALID; if (vctype == MPEG4_VCODEC_H263) { if (vc->bit_rate > 64000) /* max bitrate is 64 kbps */ return MPEG4_VIDEO_PROFILE_INVALID; if (is_valid_video_profile (profile_h263_res, sizeof (profile_h263_res), vs, vc)) return MPEG4_VIDEO_PROFILE_H263; return MPEG4_VIDEO_PROFILE_INVALID; } else if (vctype == MPEG4_VCODEC_P2) { if (vc->bit_rate <= 128000) /* SP_L2 and SP_L0B */ { if (is_valid_video_profile (profile_p2_sp_l0b_res, sizeof (profile_p2_sp_l0b_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_SP_L0B; if (is_valid_video_profile (profile_p2_sp_l2_res, sizeof (profile_p2_sp_l2_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_SP_L2; return MPEG4_VIDEO_PROFILE_INVALID; } else if (vc->bit_rate <= 384000) /* SP_L3 */ { if (is_valid_video_profile (profile_p2_sp_l3_co_res, sizeof (profile_p2_sp_l3_co_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_SP_L3; return MPEG4_VIDEO_PROFILE_INVALID; } else if (vc->bit_rate <= 2000000) /* CO and ASP_L4 */ { if (is_valid_video_profile (profile_p2_sp_l3_co_res, sizeof (profile_p2_sp_l3_co_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_ASP_L4; if (is_valid_video_profile (profile_p2_asp_l4_res, sizeof (profile_p2_asp_l4_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_ASP_L4; return MPEG4_VIDEO_PROFILE_INVALID; } else if (vc->bit_rate <= 3000000) /* SP_L3_VGA */ { if (is_valid_video_profile (profile_p2_sp_l3_vga_res, sizeof (profile_p2_sp_l3_vga_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_SP_L3_VGA; return MPEG4_VIDEO_PROFILE_INVALID; } else if (vc->bit_rate <= 8000000) /* ASP_L5 */ { if (is_valid_video_profile (profile_p2_asp_l5_res, sizeof (profile_p2_asp_l5_res), vs, vc)) return MPEG4_VIDEO_PROFILE_P2_ASP_L5; return MPEG4_VIDEO_PROFILE_INVALID; } return MPEG4_VIDEO_PROFILE_INVALID; } return MPEG4_VIDEO_PROFILE_INVALID; } static dlna_profile_t * probe_mpeg4_part2 (AVFormatContext *ctx, dlna_container_type_t st, av_codecs_t *codecs) { mpeg4_vcodec_type_t vctype; mpeg4_video_profile_t vp; audio_profile_t ap; int i; if (!stream_ctx_is_av (codecs)) return NULL; vctype = mpeg4_get_vcodec (codecs->vc); if (vctype == MPEG4_VCODEC_INVALID) return NULL; /* check for a supported container */ if (st != CT_ASF && st != CT_3GP && st != CT_MP4 && st != CT_MPEG_TRANSPORT_STREAM && st != CT_MPEG_TRANSPORT_STREAM_DLNA && st != CT_MPEG_TRANSPORT_STREAM_DLNA_NO_TS) return NULL; /* ensure we have a valid video codec bit rate */ if (codecs->vc->bit_rate == 0) codecs->vc->bit_rate = codecs->ac->bit_rate ? ctx->bit_rate - codecs->ac->bit_rate : ctx->bit_rate; /* check for valid video profile */ vp = mpeg4_video_get_profile (vctype, codecs->vs, codecs->vc); if (vp == MPEG4_VIDEO_PROFILE_INVALID) return NULL; /* check for valid audio profile */ ap = audio_profile_guess (codecs->ac); if (ap == AUDIO_PROFILE_INVALID) return NULL; /* AAC fixup: _320 profiles are audio-only profiles */ if (ap == AUDIO_PROFILE_AAC_320) ap = AUDIO_PROFILE_AAC; if (ap == AUDIO_PROFILE_AAC_HE_L2_320) ap = AUDIO_PROFILE_AAC_HE_L2; /* find profile according to container type, video and audio profiles */ for (i = 0; mpeg4_profiles_mapping[i].profile; i++) if (mpeg4_profiles_mapping[i].st == st && mpeg4_profiles_mapping[i].vp == vp && mpeg4_profiles_mapping[i].ap == ap) return mpeg4_profiles_mapping[i].profile; return NULL; } dlna_registered_profile_t dlna_profile_av_mpeg4_part2 = { .id = DLNA_PROFILE_AV_MPEG4_PART2, .class = DLNA_CLASS_AV, .extensions = "mov,hdmov,mp4,3gp,3gpp,asf,mpg,mpeg,mpe,mp2t,ts", .probe = probe_mpeg4_part2, .next = NULL };