LCOV - code coverage report
Current view: top level - src/libavfilter - af_ashowinfo.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 0 113 0.0 %
Date: 2017-09-22 10:31:19 Functions: 0 9 0.0 %

          Line data    Source code
       1             : /*
       2             :  * Copyright (c) 2011 Stefano Sabatini
       3             :  *
       4             :  * This file is part of FFmpeg.
       5             :  *
       6             :  * FFmpeg is free software; you can redistribute it and/or
       7             :  * modify it under the terms of the GNU Lesser General Public
       8             :  * License as published by the Free Software Foundation; either
       9             :  * version 2.1 of the License, or (at your option) any later version.
      10             :  *
      11             :  * FFmpeg is distributed in the hope that it will be useful,
      12             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      13             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      14             :  * Lesser General Public License for more details.
      15             :  *
      16             :  * You should have received a copy of the GNU Lesser General Public
      17             :  * License along with FFmpeg; if not, write to the Free Software
      18             :  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
      19             :  */
      20             : 
      21             : /**
      22             :  * @file
      23             :  * filter for showing textual audio frame information
      24             :  */
      25             : 
      26             : #include <inttypes.h>
      27             : #include <stddef.h>
      28             : 
      29             : #include "libavutil/adler32.h"
      30             : #include "libavutil/attributes.h"
      31             : #include "libavutil/channel_layout.h"
      32             : #include "libavutil/common.h"
      33             : #include "libavutil/downmix_info.h"
      34             : #include "libavutil/intreadwrite.h"
      35             : #include "libavutil/mem.h"
      36             : #include "libavutil/replaygain.h"
      37             : #include "libavutil/timestamp.h"
      38             : #include "libavutil/samplefmt.h"
      39             : 
      40             : #include "libavcodec/avcodec.h"
      41             : 
      42             : #include "audio.h"
      43             : #include "avfilter.h"
      44             : #include "internal.h"
      45             : 
      46             : typedef struct AShowInfoContext {
      47             :     /**
      48             :      * Scratch space for individual plane checksums for planar audio
      49             :      */
      50             :     uint32_t *plane_checksums;
      51             : } AShowInfoContext;
      52             : 
      53           0 : static av_cold void uninit(AVFilterContext *ctx)
      54             : {
      55           0 :     AShowInfoContext *s = ctx->priv;
      56           0 :     av_freep(&s->plane_checksums);
      57           0 : }
      58             : 
      59           0 : static void dump_matrixenc(AVFilterContext *ctx, AVFrameSideData *sd)
      60             : {
      61             :     enum AVMatrixEncoding enc;
      62             : 
      63           0 :     av_log(ctx, AV_LOG_INFO, "matrix encoding: ");
      64             : 
      65           0 :     if (sd->size < sizeof(enum AVMatrixEncoding)) {
      66           0 :         av_log(ctx, AV_LOG_INFO, "invalid data");
      67           0 :         return;
      68             :     }
      69             : 
      70           0 :     enc = *(enum AVMatrixEncoding *)sd->data;
      71           0 :     switch (enc) {
      72           0 :     case AV_MATRIX_ENCODING_NONE:           av_log(ctx, AV_LOG_INFO, "none");                break;
      73           0 :     case AV_MATRIX_ENCODING_DOLBY:          av_log(ctx, AV_LOG_INFO, "Dolby Surround");      break;
      74           0 :     case AV_MATRIX_ENCODING_DPLII:          av_log(ctx, AV_LOG_INFO, "Dolby Pro Logic II");  break;
      75           0 :     case AV_MATRIX_ENCODING_DPLIIX:         av_log(ctx, AV_LOG_INFO, "Dolby Pro Logic IIx"); break;
      76           0 :     case AV_MATRIX_ENCODING_DPLIIZ:         av_log(ctx, AV_LOG_INFO, "Dolby Pro Logic IIz"); break;
      77           0 :     case AV_MATRIX_ENCODING_DOLBYEX:        av_log(ctx, AV_LOG_INFO, "Dolby EX");            break;
      78           0 :     case AV_MATRIX_ENCODING_DOLBYHEADPHONE: av_log(ctx, AV_LOG_INFO, "Dolby Headphone");     break;
      79           0 :     default:                                av_log(ctx, AV_LOG_WARNING, "unknown");          break;
      80             :     }
      81             : }
      82             : 
      83           0 : static void dump_downmix(AVFilterContext *ctx, AVFrameSideData *sd)
      84             : {
      85             :     AVDownmixInfo *di;
      86             : 
      87           0 :     av_log(ctx, AV_LOG_INFO, "downmix: ");
      88           0 :     if (sd->size < sizeof(*di)) {
      89           0 :         av_log(ctx, AV_LOG_INFO, "invalid data");
      90           0 :         return;
      91             :     }
      92             : 
      93           0 :     di = (AVDownmixInfo *)sd->data;
      94             : 
      95           0 :     av_log(ctx, AV_LOG_INFO, "preferred downmix type - ");
      96           0 :     switch (di->preferred_downmix_type) {
      97           0 :     case AV_DOWNMIX_TYPE_LORO:    av_log(ctx, AV_LOG_INFO, "Lo/Ro");              break;
      98           0 :     case AV_DOWNMIX_TYPE_LTRT:    av_log(ctx, AV_LOG_INFO, "Lt/Rt");              break;
      99           0 :     case AV_DOWNMIX_TYPE_DPLII:   av_log(ctx, AV_LOG_INFO, "Dolby Pro Logic II"); break;
     100           0 :     default:                      av_log(ctx, AV_LOG_WARNING, "unknown");         break;
     101             :     }
     102             : 
     103           0 :     av_log(ctx, AV_LOG_INFO, " Mix levels: center %f (%f ltrt) - "
     104             :            "surround %f (%f ltrt) - lfe %f",
     105             :            di->center_mix_level, di->center_mix_level_ltrt,
     106             :            di->surround_mix_level, di->surround_mix_level_ltrt,
     107             :            di->lfe_mix_level);
     108             : }
     109             : 
     110           0 : static void print_gain(AVFilterContext *ctx, const char *str, int32_t gain)
     111             : {
     112           0 :     av_log(ctx, AV_LOG_INFO, "%s - ", str);
     113           0 :     if (gain == INT32_MIN)
     114           0 :         av_log(ctx, AV_LOG_INFO, "unknown");
     115             :     else
     116           0 :         av_log(ctx, AV_LOG_INFO, "%f", gain / 100000.0f);
     117           0 :     av_log(ctx, AV_LOG_INFO, ", ");
     118           0 : }
     119             : 
     120           0 : static void print_peak(AVFilterContext *ctx, const char *str, uint32_t peak)
     121             : {
     122           0 :     av_log(ctx, AV_LOG_INFO, "%s - ", str);
     123           0 :     if (!peak)
     124           0 :         av_log(ctx, AV_LOG_INFO, "unknown");
     125             :     else
     126           0 :         av_log(ctx, AV_LOG_INFO, "%f", (float)peak / UINT32_MAX);
     127           0 :     av_log(ctx, AV_LOG_INFO, ", ");
     128           0 : }
     129             : 
     130           0 : static void dump_replaygain(AVFilterContext *ctx, AVFrameSideData *sd)
     131             : {
     132             :     AVReplayGain *rg;
     133             : 
     134           0 :     av_log(ctx, AV_LOG_INFO, "replaygain: ");
     135           0 :     if (sd->size < sizeof(*rg)) {
     136           0 :         av_log(ctx, AV_LOG_INFO, "invalid data");
     137           0 :         return;
     138             :     }
     139           0 :     rg = (AVReplayGain*)sd->data;
     140             : 
     141           0 :     print_gain(ctx, "track gain", rg->track_gain);
     142           0 :     print_peak(ctx, "track peak", rg->track_peak);
     143           0 :     print_gain(ctx, "album gain", rg->album_gain);
     144           0 :     print_peak(ctx, "album peak", rg->album_peak);
     145             : }
     146             : 
     147           0 : static void dump_audio_service_type(AVFilterContext *ctx, AVFrameSideData *sd)
     148             : {
     149             :     enum AVAudioServiceType *ast;
     150             : 
     151           0 :     av_log(ctx, AV_LOG_INFO, "audio service type: ");
     152           0 :     if (sd->size < sizeof(*ast)) {
     153           0 :         av_log(ctx, AV_LOG_INFO, "invalid data");
     154           0 :         return;
     155             :     }
     156           0 :     ast = (enum AVAudioServiceType*)sd->data;
     157           0 :     switch (*ast) {
     158           0 :     case AV_AUDIO_SERVICE_TYPE_MAIN:              av_log(ctx, AV_LOG_INFO, "Main Audio Service"); break;
     159           0 :     case AV_AUDIO_SERVICE_TYPE_EFFECTS:           av_log(ctx, AV_LOG_INFO, "Effects");            break;
     160           0 :     case AV_AUDIO_SERVICE_TYPE_VISUALLY_IMPAIRED: av_log(ctx, AV_LOG_INFO, "Visually Impaired");  break;
     161           0 :     case AV_AUDIO_SERVICE_TYPE_HEARING_IMPAIRED:  av_log(ctx, AV_LOG_INFO, "Hearing Impaired");   break;
     162           0 :     case AV_AUDIO_SERVICE_TYPE_DIALOGUE:          av_log(ctx, AV_LOG_INFO, "Dialogue");           break;
     163           0 :     case AV_AUDIO_SERVICE_TYPE_COMMENTARY:        av_log(ctx, AV_LOG_INFO, "Commentary");         break;
     164           0 :     case AV_AUDIO_SERVICE_TYPE_EMERGENCY:         av_log(ctx, AV_LOG_INFO, "Emergency");          break;
     165           0 :     case AV_AUDIO_SERVICE_TYPE_VOICE_OVER:        av_log(ctx, AV_LOG_INFO, "Voice Over");         break;
     166           0 :     case AV_AUDIO_SERVICE_TYPE_KARAOKE:           av_log(ctx, AV_LOG_INFO, "Karaoke");            break;
     167           0 :     default:                                      av_log(ctx, AV_LOG_INFO, "unknown");            break;
     168             :     }
     169             : }
     170             : 
     171           0 : static void dump_unknown(AVFilterContext *ctx, AVFrameSideData *sd)
     172             : {
     173           0 :     av_log(ctx, AV_LOG_INFO, "unknown side data type: %d, size %d bytes", sd->type, sd->size);
     174           0 : }
     175             : 
     176           0 : static int filter_frame(AVFilterLink *inlink, AVFrame *buf)
     177             : {
     178           0 :     AVFilterContext *ctx = inlink->dst;
     179           0 :     AShowInfoContext *s  = ctx->priv;
     180             :     char chlayout_str[128];
     181           0 :     uint32_t checksum = 0;
     182           0 :     int channels    = inlink->channels;
     183           0 :     int planar      = av_sample_fmt_is_planar(buf->format);
     184           0 :     int block_align = av_get_bytes_per_sample(buf->format) * (planar ? 1 : channels);
     185           0 :     int data_size   = buf->nb_samples * block_align;
     186           0 :     int planes      = planar ? channels : 1;
     187             :     int i;
     188           0 :     void *tmp_ptr = av_realloc_array(s->plane_checksums, channels, sizeof(*s->plane_checksums));
     189             : 
     190           0 :     if (!tmp_ptr)
     191           0 :         return AVERROR(ENOMEM);
     192           0 :     s->plane_checksums = tmp_ptr;
     193             : 
     194           0 :     for (i = 0; i < planes; i++) {
     195           0 :         uint8_t *data = buf->extended_data[i];
     196             : 
     197           0 :         s->plane_checksums[i] = av_adler32_update(0, data, data_size);
     198           0 :         checksum = i ? av_adler32_update(checksum, data, data_size) :
     199           0 :                        s->plane_checksums[0];
     200             :     }
     201             : 
     202           0 :     av_get_channel_layout_string(chlayout_str, sizeof(chlayout_str), buf->channels,
     203             :                                  buf->channel_layout);
     204             : 
     205           0 :     av_log(ctx, AV_LOG_INFO,
     206             :            "n:%"PRId64" pts:%s pts_time:%s pos:%"PRId64" "
     207             :            "fmt:%s channels:%d chlayout:%s rate:%d nb_samples:%d "
     208             :            "checksum:%08"PRIX32" ",
     209             :            inlink->frame_count_out,
     210           0 :            av_ts2str(buf->pts), av_ts2timestr(buf->pts, &inlink->time_base),
     211             :            buf->pkt_pos,
     212           0 :            av_get_sample_fmt_name(buf->format), buf->channels, chlayout_str,
     213             :            buf->sample_rate, buf->nb_samples,
     214             :            checksum);
     215             : 
     216           0 :     av_log(ctx, AV_LOG_INFO, "plane_checksums: [ ");
     217           0 :     for (i = 0; i < planes; i++)
     218           0 :         av_log(ctx, AV_LOG_INFO, "%08"PRIX32" ", s->plane_checksums[i]);
     219           0 :     av_log(ctx, AV_LOG_INFO, "]\n");
     220             : 
     221           0 :     for (i = 0; i < buf->nb_side_data; i++) {
     222           0 :         AVFrameSideData *sd = buf->side_data[i];
     223             : 
     224           0 :         av_log(ctx, AV_LOG_INFO, "  side data - ");
     225           0 :         switch (sd->type) {
     226           0 :         case AV_FRAME_DATA_MATRIXENCODING: dump_matrixenc (ctx, sd); break;
     227           0 :         case AV_FRAME_DATA_DOWNMIX_INFO:   dump_downmix   (ctx, sd); break;
     228           0 :         case AV_FRAME_DATA_REPLAYGAIN:     dump_replaygain(ctx, sd); break;
     229           0 :         case AV_FRAME_DATA_AUDIO_SERVICE_TYPE: dump_audio_service_type(ctx, sd); break;
     230           0 :         default:                           dump_unknown   (ctx, sd); break;
     231             :         }
     232             : 
     233           0 :         av_log(ctx, AV_LOG_INFO, "\n");
     234             :     }
     235             : 
     236           0 :     return ff_filter_frame(inlink->dst->outputs[0], buf);
     237             : }
     238             : 
     239             : static const AVFilterPad inputs[] = {
     240             :     {
     241             :         .name         = "default",
     242             :         .type         = AVMEDIA_TYPE_AUDIO,
     243             :         .filter_frame = filter_frame,
     244             :     },
     245             :     { NULL }
     246             : };
     247             : 
     248             : static const AVFilterPad outputs[] = {
     249             :     {
     250             :         .name = "default",
     251             :         .type = AVMEDIA_TYPE_AUDIO,
     252             :     },
     253             :     { NULL }
     254             : };
     255             : 
     256             : AVFilter ff_af_ashowinfo = {
     257             :     .name        = "ashowinfo",
     258             :     .description = NULL_IF_CONFIG_SMALL("Show textual information for each audio frame."),
     259             :     .priv_size   = sizeof(AShowInfoContext),
     260             :     .uninit      = uninit,
     261             :     .inputs      = inputs,
     262             :     .outputs     = outputs,
     263             : };

Generated by: LCOV version 1.13