std::string get_codec_name(AVCodecContext *pCodecCtx) { AVCodecID id = pCodecCtx->codec_id; // Grab the codec AVCodec *p = avcodec_find_decoder(id); const char *profile = p ? av_get_profile_name(p, pCodecCtx->profile) : nullptr; std::ostringstream codec_name; const char *nice_name = nullptr; for (int i = 0; i < countof(nice_codec_names); ++i) { if (nice_codec_names[i].id == id) { nice_name = nice_codec_names[i].name; break; } } if (id == AV_CODEC_ID_DTS && pCodecCtx->codec_tag == 0xA2) { profile = "DTS Express"; } if (id == AV_CODEC_ID_H264 && profile) { codec_name << nice_name << " " << tolower(profile); if (pCodecCtx->level && pCodecCtx->level != FF_LEVEL_UNKNOWN && pCodecCtx->level < 1000) { char l_buf[5]; sprintf_s(l_buf, "%.1f", pCodecCtx->level / 10.0); codec_name << " L" << l_buf; } } else if (id == AV_CODEC_ID_VC1 && profile) { codec_name << nice_name << " " << tolower(profile); if (pCodecCtx->level != FF_LEVEL_UNKNOWN) { codec_name << " L" << pCodecCtx->level; } } else if (id == AV_CODEC_ID_DTS && profile) { codec_name << tolower(profile); } else if (id == AV_CODEC_ID_JPEG2000 && profile) { codec_name << tolower(profile); } else if (nice_name) { codec_name << nice_name; if (profile) codec_name << " " << tolower(profile); } else if (p && p->name) { codec_name << p->name; if (profile) codec_name << " " << tolower(profile); } else if (pCodecCtx->codec_name[0] != '\0') { codec_name << pCodecCtx->codec_name; } else { /* output avi tags */ char buf[32]; av_get_codec_tag_string(buf, sizeof(buf), pCodecCtx->codec_tag); codec_name << buf; sprintf_s(buf, "0x%04X", pCodecCtx->codec_tag); codec_name << " / " << buf; } return codec_name.str(); }
void ijkmeta_set_avformat_context_l(IjkMediaMeta *meta, AVFormatContext *ic) { if (!meta || !ic) return; if (ic->iformat && ic->iformat->name) ijkmeta_set_string_l(meta, IJKM_KEY_FORMAT, ic->iformat->name); if (ic->duration != AV_NOPTS_VALUE) ijkmeta_set_int64_l(meta, IJKM_KEY_DURATION_US, ic->duration); if (ic->start_time != AV_NOPTS_VALUE) ijkmeta_set_int64_l(meta, IJKM_KEY_START_US, ic->start_time); if (ic->bit_rate) ijkmeta_set_int64_l(meta, IJKM_KEY_BITRATE, ic->bit_rate); IjkMediaMeta *stream_meta = NULL; for (int i = 0; i < ic->nb_streams; i++) { if (!stream_meta) ijkmeta_destroy_p(&stream_meta); AVStream *st = ic->streams[i]; if (!st || !st->codec) continue; stream_meta = ijkmeta_create(); if (!stream_meta) continue; AVCodecContext *avctx = st->codec; const char *codec_name = avcodec_get_name(avctx->codec_id); if (codec_name) ijkmeta_set_string_l(stream_meta, IJKM_KEY_CODEC_NAME, codec_name); if (avctx->profile != FF_PROFILE_UNKNOWN) { const AVCodec *codec = avctx->codec ? avctx->codec : avcodec_find_decoder(avctx->codec_id); if (codec) { const char *profile = av_get_profile_name(codec, avctx->profile); if (profile) ijkmeta_set_string_l(stream_meta, IJKM_KEY_CODEC_PROFILE, profile); if (codec->long_name) ijkmeta_set_string_l(stream_meta, IJKM_KEY_CODEC_LONG_NAME, codec->long_name); ijkmeta_set_int64_l(stream_meta, IJKM_KEY_CODEC_LEVEL, avctx->level); if (avctx->pix_fmt != AV_PIX_FMT_NONE) ijkmeta_set_string_l(stream_meta, IJKM_KEY_CODEC_PIXEL_FORMAT, av_get_pix_fmt_name(avctx->pix_fmt)); } } int64_t bitrate = get_bit_rate(avctx); if (bitrate > 0) { ijkmeta_set_int64_l(stream_meta, IJKM_KEY_BITRATE, bitrate); } switch (avctx->codec_type) { case AVMEDIA_TYPE_VIDEO: { ijkmeta_set_string_l(stream_meta, IJKM_KEY_TYPE, IJKM_VAL_TYPE__VIDEO); if (avctx->width > 0) ijkmeta_set_int64_l(stream_meta, IJKM_KEY_WIDTH, avctx->width); if (avctx->height > 0) ijkmeta_set_int64_l(stream_meta, IJKM_KEY_HEIGHT, avctx->height); if (st->sample_aspect_ratio.num > 0 && st->sample_aspect_ratio.den > 0) { ijkmeta_set_int64_l(stream_meta, IJKM_KEY_SAR_NUM, avctx->sample_aspect_ratio.num); ijkmeta_set_int64_l(stream_meta, IJKM_KEY_SAR_DEN, avctx->sample_aspect_ratio.den); } if (st->avg_frame_rate.num > 0 && st->avg_frame_rate.den > 0) { ijkmeta_set_int64_l(stream_meta, IJKM_KEY_FPS_NUM, st->avg_frame_rate.num); ijkmeta_set_int64_l(stream_meta, IJKM_KEY_FPS_DEN, st->avg_frame_rate.den); } if (st->r_frame_rate.num > 0 && st->r_frame_rate.den > 0) { ijkmeta_set_int64_l(stream_meta, IJKM_KEY_TBR_NUM, st->avg_frame_rate.num); ijkmeta_set_int64_l(stream_meta, IJKM_KEY_TBR_DEN, st->avg_frame_rate.den); } break; } case AVMEDIA_TYPE_AUDIO: { ijkmeta_set_string_l(stream_meta, IJKM_KEY_TYPE, IJKM_VAL_TYPE__AUDIO); if (avctx->sample_rate) ijkmeta_set_int64_l(stream_meta, IJKM_KEY_SAMPLE_RATE, avctx->sample_rate); if (avctx->channel_layout) ijkmeta_set_int64_l(stream_meta, IJKM_KEY_CHANNEL_LAYOUT, avctx->channel_layout); break; } default: { ijkmeta_set_string_l(stream_meta, IJKM_KEY_TYPE, IJKM_VAL_TYPE__UNKNOWN); break; } } AVDictionaryEntry *lang = av_dict_get(st->metadata, "language", NULL, 0); if (lang && lang->value) ijkmeta_set_string_l(stream_meta, IJKM_KEY_LANGUAGE, lang->value); ijkmeta_append_child_l(meta, stream_meta); stream_meta = NULL; } if (!stream_meta) ijkmeta_destroy_p(&stream_meta); }
static void show_stream(AVFormatContext *fmt_ctx, int stream_idx) { AVStream *stream = fmt_ctx->streams[stream_idx]; AVCodecContext *dec_ctx; const AVCodec *dec; const char *profile; char val_str[128]; AVRational display_aspect_ratio, *sar = NULL; const AVPixFmtDescriptor *desc; probe_object_header("stream"); probe_int("index", stream->index); if ((dec_ctx = stream->codec)) { if ((dec = dec_ctx->codec)) { probe_str("codec_name", dec->name); probe_str("codec_long_name", dec->long_name); } else { probe_str("codec_name", "unknown"); } probe_str("codec_type", media_type_string(dec_ctx->codec_type)); probe_str("codec_time_base", rational_string(val_str, sizeof(val_str), "/", &dec_ctx->time_base)); /* print AVI/FourCC tag */ av_get_codec_tag_string(val_str, sizeof(val_str), dec_ctx->codec_tag); probe_str("codec_tag_string", val_str); probe_str("codec_tag", tag_string(val_str, sizeof(val_str), dec_ctx->codec_tag)); /* print profile, if there is one */ if (dec && (profile = av_get_profile_name(dec, dec_ctx->profile))) probe_str("profile", profile); switch (dec_ctx->codec_type) { case AVMEDIA_TYPE_VIDEO: probe_int("width", dec_ctx->width); probe_int("height", dec_ctx->height); probe_int("coded_width", dec_ctx->coded_width); probe_int("coded_height", dec_ctx->coded_height); probe_int("has_b_frames", dec_ctx->has_b_frames); if (dec_ctx->sample_aspect_ratio.num) sar = &dec_ctx->sample_aspect_ratio; else if (stream->sample_aspect_ratio.num) sar = &stream->sample_aspect_ratio; if (sar) { probe_str("sample_aspect_ratio", rational_string(val_str, sizeof(val_str), ":", sar)); av_reduce(&display_aspect_ratio.num, &display_aspect_ratio.den, dec_ctx->width * sar->num, dec_ctx->height * sar->den, 1024*1024); probe_str("display_aspect_ratio", rational_string(val_str, sizeof(val_str), ":", &display_aspect_ratio)); } desc = av_pix_fmt_desc_get(dec_ctx->pix_fmt); probe_str("pix_fmt", desc ? desc->name : "unknown"); probe_int("level", dec_ctx->level); probe_str("color_range", av_color_range_name(dec_ctx->color_range)); probe_str("color_space", av_color_space_name(dec_ctx->colorspace)); probe_str("color_trc", av_color_transfer_name(dec_ctx->color_trc)); probe_str("color_pri", av_color_primaries_name(dec_ctx->color_primaries)); probe_str("chroma_loc", av_chroma_location_name(dec_ctx->chroma_sample_location)); break; case AVMEDIA_TYPE_AUDIO: probe_str("sample_rate", value_string(val_str, sizeof(val_str), dec_ctx->sample_rate, unit_hertz_str)); probe_int("channels", dec_ctx->channels); probe_int("bits_per_sample", av_get_bits_per_sample(dec_ctx->codec_id)); break; } } else { probe_str("codec_type", "unknown"); } if (fmt_ctx->iformat->flags & AVFMT_SHOW_IDS) probe_int("id", stream->id); probe_str("avg_frame_rate", rational_string(val_str, sizeof(val_str), "/", &stream->avg_frame_rate)); if (dec_ctx->bit_rate) probe_str("bit_rate", value_string(val_str, sizeof(val_str), dec_ctx->bit_rate, unit_bit_per_second_str)); probe_str("time_base", rational_string(val_str, sizeof(val_str), "/", &stream->time_base)); probe_str("start_time", time_value_string(val_str, sizeof(val_str), stream->start_time, &stream->time_base)); probe_str("duration", time_value_string(val_str, sizeof(val_str), stream->duration, &stream->time_base)); if (stream->nb_frames) probe_int("nb_frames", stream->nb_frames); probe_dict(stream->metadata, "tags"); if (stream->nb_side_data) { int i, j; probe_object_header("sidedata"); for (i = 0; i < stream->nb_side_data; i++) { const AVPacketSideData* sd = &stream->side_data[i]; switch (sd->type) { case AV_PKT_DATA_DISPLAYMATRIX: probe_object_header("displaymatrix"); probe_array_header("matrix", 1); for (j = 0; j < 9; j++) probe_int(NULL, ((int32_t *)sd->data)[j]); probe_array_footer("matrix", 1); probe_int("rotation", av_display_rotation_get((int32_t *)sd->data)); probe_object_footer("displaymatrix"); break; } } probe_object_footer("sidedata"); } probe_object_footer("stream"); }
static void show_stream(AVFormatContext *fmt_ctx, int stream_idx) { AVStream *stream = fmt_ctx->streams[stream_idx]; AVCodecContext *dec_ctx; AVCodec *dec; const char *profile; char val_str[128]; AVRational display_aspect_ratio; probe_object_header("stream"); probe_int("index", stream->index); if ((dec_ctx = stream->codec)) { if ((dec = dec_ctx->codec)) { probe_str("codec_name", dec->name); probe_str("codec_long_name", dec->long_name); } else { probe_str("codec_name", "unknown"); } probe_str("codec_type", media_type_string(dec_ctx->codec_type)); probe_str("codec_time_base", rational_string(val_str, sizeof(val_str), "/", &dec_ctx->time_base)); /* print AVI/FourCC tag */ av_get_codec_tag_string(val_str, sizeof(val_str), dec_ctx->codec_tag); probe_str("codec_tag_string", val_str); probe_str("codec_tag", tag_string(val_str, sizeof(val_str), dec_ctx->codec_tag)); /* print profile, if there is one */ if (dec && (profile = av_get_profile_name(dec, dec_ctx->profile))) probe_str("profile", profile); switch (dec_ctx->codec_type) { case AVMEDIA_TYPE_VIDEO: probe_int("width", dec_ctx->width); probe_int("height", dec_ctx->height); probe_int("has_b_frames", dec_ctx->has_b_frames); if (dec_ctx->sample_aspect_ratio.num) { probe_str("sample_aspect_ratio", rational_string(val_str, sizeof(val_str), ":", &dec_ctx->sample_aspect_ratio)); av_reduce(&display_aspect_ratio.num, &display_aspect_ratio.den, dec_ctx->width * dec_ctx->sample_aspect_ratio.num, dec_ctx->height * dec_ctx->sample_aspect_ratio.den, 1024*1024); probe_str("display_aspect_ratio", rational_string(val_str, sizeof(val_str), ":", &display_aspect_ratio)); } probe_str("pix_fmt", dec_ctx->pix_fmt != PIX_FMT_NONE ? av_pix_fmt_descriptors[dec_ctx->pix_fmt].name : "unknown"); probe_int("level", dec_ctx->level); break; case AVMEDIA_TYPE_AUDIO: probe_str("sample_rate", value_string(val_str, sizeof(val_str), dec_ctx->sample_rate, unit_hertz_str)); probe_int("channels", dec_ctx->channels); probe_int("bits_per_sample", av_get_bits_per_sample(dec_ctx->codec_id)); break; } } else { probe_str("codec_type", "unknown"); } if (fmt_ctx->iformat->flags & AVFMT_SHOW_IDS) probe_int("id", stream->id); probe_str("avg_frame_rate", rational_string(val_str, sizeof(val_str), "/", &stream->avg_frame_rate)); probe_str("time_base", rational_string(val_str, sizeof(val_str), "/", &stream->time_base)); probe_str("start_time", time_value_string(val_str, sizeof(val_str), stream->start_time, &stream->time_base)); probe_str("duration", time_value_string(val_str, sizeof(val_str), stream->duration, &stream->time_base)); if (stream->nb_frames) probe_int("nb_frames", stream->nb_frames); probe_dict(stream->metadata, "tags"); probe_object_footer("stream"); }