LCOV - code coverage report
Current view: top level - libavfilter - f_drawgraph.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 0 217 0.0 %
Date: 2017-12-16 13:57:32 Functions: 0 8 0.0 %

          Line data    Source code
       1             : /*
       2             :  * Copyright (c) 2015 Paul B Mahol
       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             : #include "float.h"
      22             : 
      23             : #include "libavutil/eval.h"
      24             : #include "libavutil/intreadwrite.h"
      25             : #include "libavutil/opt.h"
      26             : #include "avfilter.h"
      27             : #include "formats.h"
      28             : #include "internal.h"
      29             : #include "video.h"
      30             : 
      31             : typedef struct DrawGraphContext {
      32             :     const AVClass *class;
      33             : 
      34             :     char          *key[4];
      35             :     float         min, max;
      36             :     char          *fg_str[4];
      37             :     AVExpr        *fg_expr[4];
      38             :     uint8_t       bg[4];
      39             :     int           mode;
      40             :     int           slide;
      41             :     int           w, h;
      42             : 
      43             :     AVFrame       *out;
      44             :     int           x;
      45             :     int           prev_y[4];
      46             :     int           first;
      47             :     float         *values[4];
      48             :     int           values_size[4];
      49             :     int           nb_values;
      50             : } DrawGraphContext;
      51             : 
      52             : #define OFFSET(x) offsetof(DrawGraphContext, x)
      53             : #define FLAGS AV_OPT_FLAG_VIDEO_PARAM|AV_OPT_FLAG_FILTERING_PARAM
      54             : 
      55             : static const AVOption drawgraph_options[] = {
      56             :     { "m1", "set 1st metadata key", OFFSET(key[0]), AV_OPT_TYPE_STRING, {.str=""}, CHAR_MIN, CHAR_MAX, FLAGS },
      57             :     { "fg1", "set 1st foreground color expression", OFFSET(fg_str[0]), AV_OPT_TYPE_STRING, {.str="0xffff0000"}, CHAR_MIN, CHAR_MAX, FLAGS },
      58             :     { "m2", "set 2nd metadata key", OFFSET(key[1]), AV_OPT_TYPE_STRING, {.str=""}, CHAR_MIN, CHAR_MAX, FLAGS },
      59             :     { "fg2", "set 2nd foreground color expression", OFFSET(fg_str[1]), AV_OPT_TYPE_STRING, {.str="0xff00ff00"}, CHAR_MIN, CHAR_MAX, FLAGS },
      60             :     { "m3", "set 3rd metadata key", OFFSET(key[2]), AV_OPT_TYPE_STRING, {.str=""}, CHAR_MIN, CHAR_MAX, FLAGS },
      61             :     { "fg3", "set 3rd foreground color expression", OFFSET(fg_str[2]), AV_OPT_TYPE_STRING, {.str="0xffff00ff"}, CHAR_MIN, CHAR_MAX, FLAGS },
      62             :     { "m4", "set 4th metadata key", OFFSET(key[3]), AV_OPT_TYPE_STRING, {.str=""}, CHAR_MIN, CHAR_MAX, FLAGS },
      63             :     { "fg4", "set 4th foreground color expression", OFFSET(fg_str[3]), AV_OPT_TYPE_STRING, {.str="0xffffff00"}, CHAR_MIN, CHAR_MAX, FLAGS },
      64             :     { "bg", "set background color", OFFSET(bg), AV_OPT_TYPE_COLOR, {.str="white"}, CHAR_MIN, CHAR_MAX, FLAGS },
      65             :     { "min", "set minimal value", OFFSET(min), AV_OPT_TYPE_FLOAT, {.dbl=-1.}, INT_MIN, INT_MAX, FLAGS },
      66             :     { "max", "set maximal value", OFFSET(max), AV_OPT_TYPE_FLOAT, {.dbl=1.}, INT_MIN, INT_MAX, FLAGS },
      67             :     { "mode", "set graph mode", OFFSET(mode), AV_OPT_TYPE_INT, {.i64=2}, 0, 2, FLAGS, "mode" },
      68             :         {"bar", "draw bars", OFFSET(mode), AV_OPT_TYPE_CONST, {.i64=0}, 0, 0, FLAGS, "mode"},
      69             :         {"dot", "draw dots", OFFSET(mode), AV_OPT_TYPE_CONST, {.i64=1}, 0, 0, FLAGS, "mode"},
      70             :         {"line", "draw lines", OFFSET(mode), AV_OPT_TYPE_CONST, {.i64=2}, 0, 0, FLAGS, "mode"},
      71             :     { "slide", "set slide mode", OFFSET(slide), AV_OPT_TYPE_INT, {.i64=0}, 0, 4, FLAGS, "slide" },
      72             :         {"frame", "draw new frames", OFFSET(slide), AV_OPT_TYPE_CONST, {.i64=0}, 0, 0, FLAGS, "slide"},
      73             :         {"replace", "replace old columns with new", OFFSET(slide), AV_OPT_TYPE_CONST, {.i64=1}, 0, 0, FLAGS, "slide"},
      74             :         {"scroll", "scroll from right to left", OFFSET(slide), AV_OPT_TYPE_CONST, {.i64=2}, 0, 0, FLAGS, "slide"},
      75             :         {"rscroll", "scroll from left to right", OFFSET(slide), AV_OPT_TYPE_CONST, {.i64=3}, 0, 0, FLAGS, "slide"},
      76             :         {"picture", "display graph in single frame", OFFSET(slide), AV_OPT_TYPE_CONST, {.i64=4}, 0, 0, FLAGS, "slide"},
      77             :     { "size", "set graph size", OFFSET(w), AV_OPT_TYPE_IMAGE_SIZE, {.str="900x256"}, 0, 0, FLAGS },
      78             :     { "s", "set graph size", OFFSET(w), AV_OPT_TYPE_IMAGE_SIZE, {.str="900x256"}, 0, 0, FLAGS },
      79             :     { NULL }
      80             : };
      81             : 
      82             : static const char *const var_names[] = {   "MAX",   "MIN",   "VAL", NULL };
      83             : enum                                   { VAR_MAX, VAR_MIN, VAR_VAL, VAR_VARS_NB };
      84             : 
      85           0 : static av_cold int init(AVFilterContext *ctx)
      86             : {
      87           0 :     DrawGraphContext *s = ctx->priv;
      88             :     int ret, i;
      89             : 
      90           0 :     if (s->max <= s->min) {
      91           0 :         av_log(ctx, AV_LOG_ERROR, "max is same or lower than min\n");
      92           0 :         return AVERROR(EINVAL);
      93             :     }
      94             : 
      95           0 :     for (i = 0; i < 4; i++) {
      96           0 :         if (s->fg_str[i]) {
      97           0 :             ret = av_expr_parse(&s->fg_expr[i], s->fg_str[i], var_names,
      98             :                                 NULL, NULL, NULL, NULL, 0, ctx);
      99             : 
     100           0 :             if (ret < 0)
     101           0 :                 return ret;
     102             :         }
     103             :     }
     104             : 
     105           0 :     s->first = 1;
     106             : 
     107           0 :     if (s->slide == 4) {
     108           0 :         s->values[0] = av_fast_realloc(NULL, &s->values_size[0], 2000);
     109           0 :         s->values[1] = av_fast_realloc(NULL, &s->values_size[1], 2000);
     110           0 :         s->values[2] = av_fast_realloc(NULL, &s->values_size[2], 2000);
     111           0 :         s->values[3] = av_fast_realloc(NULL, &s->values_size[3], 2000);
     112             : 
     113           0 :         if (!s->values[0] || !s->values[1] ||
     114           0 :             !s->values[2] || !s->values[3]) {
     115           0 :             return AVERROR(ENOMEM);
     116             :         }
     117             :     }
     118             : 
     119           0 :     return 0;
     120             : }
     121             : 
     122           0 : static int query_formats(AVFilterContext *ctx)
     123             : {
     124           0 :     AVFilterLink *outlink = ctx->outputs[0];
     125             :     static const enum AVPixelFormat pix_fmts[] = {
     126             :         AV_PIX_FMT_RGBA,
     127             :         AV_PIX_FMT_NONE
     128             :     };
     129             :     int ret;
     130             : 
     131           0 :     AVFilterFormats *fmts_list = ff_make_format_list(pix_fmts);
     132           0 :     if ((ret = ff_formats_ref(fmts_list, &outlink->in_formats)) < 0)
     133           0 :         return ret;
     134             : 
     135           0 :     return 0;
     136             : }
     137             : 
     138           0 : static void clear_image(DrawGraphContext *s, AVFrame *out, AVFilterLink *outlink)
     139             : {
     140             :     int i, j;
     141           0 :     int bg = AV_RN32(s->bg);
     142             : 
     143           0 :     for (i = 0; i < out->height; i++)
     144           0 :         for (j = 0; j < out->width; j++)
     145           0 :             AV_WN32(out->data[0] + i * out->linesize[0] + j * 4, bg);
     146           0 : }
     147             : 
     148           0 : static inline void draw_dot(int fg, int x, int y, AVFrame *out)
     149             : {
     150           0 :     AV_WN32(out->data[0] + y * out->linesize[0] + x * 4, fg);
     151           0 : }
     152             : 
     153           0 : static int filter_frame(AVFilterLink *inlink, AVFrame *in)
     154             : {
     155           0 :     AVFilterContext *ctx = inlink->dst;
     156           0 :     DrawGraphContext *s = ctx->priv;
     157           0 :     AVFilterLink *outlink = ctx->outputs[0];
     158             :     AVDictionary *metadata;
     159             :     AVDictionaryEntry *e;
     160           0 :     AVFrame *out = s->out;
     161             :     int i;
     162             : 
     163           0 :     if (s->slide == 4 && s->nb_values >= s->values_size[0] / sizeof(float)) {
     164             :         float *ptr;
     165             : 
     166           0 :         ptr = av_fast_realloc(s->values[0], &s->values_size[0], s->values_size[0] * 2);
     167           0 :         if (!ptr)
     168           0 :             return AVERROR(ENOMEM);
     169           0 :         s->values[0] = ptr;
     170             : 
     171           0 :         ptr = av_fast_realloc(s->values[1], &s->values_size[1], s->values_size[1] * 2);
     172           0 :         if (!ptr)
     173           0 :             return AVERROR(ENOMEM);
     174           0 :         s->values[1] = ptr;
     175             : 
     176           0 :         ptr = av_fast_realloc(s->values[2], &s->values_size[2], s->values_size[2] * 2);
     177           0 :         if (!ptr)
     178           0 :             return AVERROR(ENOMEM);
     179           0 :         s->values[2] = ptr;
     180             : 
     181           0 :         ptr = av_fast_realloc(s->values[3], &s->values_size[3], s->values_size[3] * 2);
     182           0 :         if (!ptr)
     183           0 :             return AVERROR(ENOMEM);
     184           0 :         s->values[3] = ptr;
     185             :     }
     186             : 
     187           0 :     if (s->slide != 4 || s->nb_values == 0) {
     188           0 :         if (!s->out || s->out->width  != outlink->w ||
     189           0 :                        s->out->height != outlink->h) {
     190           0 :             av_frame_free(&s->out);
     191           0 :             s->out = ff_get_video_buffer(outlink, outlink->w, outlink->h);
     192           0 :             out = s->out;
     193           0 :             if (!s->out) {
     194           0 :                 av_frame_free(&in);
     195           0 :                 return AVERROR(ENOMEM);
     196             :             }
     197             : 
     198           0 :             clear_image(s, out, outlink);
     199             :         }
     200           0 :         av_frame_copy_props(out, in);
     201             :     }
     202             : 
     203           0 :     metadata = in->metadata;
     204             : 
     205           0 :     for (i = 0; i < 4; i++) {
     206             :         double values[VAR_VARS_NB];
     207             :         int j, y, x, old;
     208             :         uint32_t fg, bg;
     209             :         float vf;
     210             : 
     211           0 :         if (s->slide == 4)
     212           0 :             s->values[i][s->nb_values] = NAN;
     213             : 
     214           0 :         e = av_dict_get(metadata, s->key[i], NULL, 0);
     215           0 :         if (!e || !e->value)
     216           0 :             continue;
     217             : 
     218           0 :         if (sscanf(e->value, "%f", &vf) != 1)
     219           0 :             continue;
     220             : 
     221           0 :         vf = av_clipf(vf, s->min, s->max);
     222             : 
     223           0 :         if (s->slide == 4) {
     224           0 :             s->values[i][s->nb_values] = vf;
     225           0 :             continue;
     226             :         }
     227             : 
     228           0 :         values[VAR_MIN] = s->min;
     229           0 :         values[VAR_MAX] = s->max;
     230           0 :         values[VAR_VAL] = vf;
     231             : 
     232           0 :         fg = av_expr_eval(s->fg_expr[i], values, NULL);
     233           0 :         bg = AV_RN32(s->bg);
     234             : 
     235           0 :         if (i == 0 && (s->x >= outlink->w || s->slide == 3)) {
     236           0 :             if (s->slide == 0 || s->slide == 1)
     237           0 :                 s->x = 0;
     238             : 
     239           0 :             if (s->slide == 2) {
     240           0 :                 s->x = outlink->w - 1;
     241           0 :                 for (j = 0; j < outlink->h; j++) {
     242           0 :                     memmove(out->data[0] + j * out->linesize[0] ,
     243           0 :                             out->data[0] + j * out->linesize[0] + 4,
     244           0 :                             (outlink->w - 1) * 4);
     245             :                 }
     246           0 :             } else if (s->slide == 3) {
     247           0 :                 s->x = 0;
     248           0 :                 for (j = 0; j < outlink->h; j++) {
     249           0 :                     memmove(out->data[0] + j * out->linesize[0] + 4,
     250           0 :                             out->data[0] + j * out->linesize[0],
     251           0 :                             (outlink->w - 1) * 4);
     252             :                 }
     253           0 :             } else if (s->slide == 0) {
     254           0 :                 clear_image(s, out, outlink);
     255             :             }
     256             :         }
     257             : 
     258           0 :         x = s->x;
     259           0 :         y = (outlink->h - 1) * (1 - ((vf - s->min) / (s->max - s->min)));
     260             : 
     261           0 :         switch (s->mode) {
     262           0 :         case 0:
     263           0 :             if (i == 0 && (s->slide > 0))
     264           0 :                 for (j = 0; j < outlink->h; j++)
     265           0 :                     draw_dot(bg, x, j, out);
     266             : 
     267           0 :             old = AV_RN32(out->data[0] + y * out->linesize[0] + x * 4);
     268           0 :             for (j = y; j < outlink->h; j++) {
     269           0 :                 if (old != bg &&
     270           0 :                     (AV_RN32(out->data[0] + j * out->linesize[0] + x * 4) != old) ||
     271           0 :                     AV_RN32(out->data[0] + FFMIN(j+1, outlink->h - 1) * out->linesize[0] + x * 4) != old) {
     272           0 :                     draw_dot(fg, x, j, out);
     273           0 :                     break;
     274             :                 }
     275           0 :                 draw_dot(fg, x, j, out);
     276             :             }
     277           0 :             break;
     278           0 :         case 1:
     279           0 :             if (i == 0 && (s->slide > 0))
     280           0 :                 for (j = 0; j < outlink->h; j++)
     281           0 :                     draw_dot(bg, x, j, out);
     282           0 :             draw_dot(fg, x, y, out);
     283           0 :             break;
     284           0 :         case 2:
     285           0 :             if (s->first) {
     286           0 :                 s->first = 0;
     287           0 :                 s->prev_y[i] = y;
     288             :             }
     289             : 
     290           0 :             if (i == 0 && (s->slide > 0)) {
     291           0 :                 for (j = 0; j < y; j++)
     292           0 :                     draw_dot(bg, x, j, out);
     293           0 :                 for (j = outlink->h - 1; j > y; j--)
     294           0 :                     draw_dot(bg, x, j, out);
     295             :             }
     296           0 :             if (y <= s->prev_y[i]) {
     297           0 :                 for (j = y; j <= s->prev_y[i]; j++)
     298           0 :                     draw_dot(fg, x, j, out);
     299             :             } else {
     300           0 :                 for (j = s->prev_y[i]; j <= y; j++)
     301           0 :                     draw_dot(fg, x, j, out);
     302             :             }
     303           0 :             s->prev_y[i] = y;
     304           0 :             break;
     305             :         }
     306             :     }
     307             : 
     308           0 :     s->nb_values++;
     309           0 :     s->x++;
     310             : 
     311           0 :     av_frame_free(&in);
     312             : 
     313           0 :     if (s->slide == 4)
     314           0 :         return 0;
     315             : 
     316           0 :     return ff_filter_frame(outlink, av_frame_clone(s->out));
     317             : }
     318             : 
     319           0 : static int request_frame(AVFilterLink *outlink)
     320             : {
     321           0 :     AVFilterContext *ctx = outlink->src;
     322           0 :     DrawGraphContext *s = ctx->priv;
     323           0 :     AVFrame *out = s->out;
     324             :     int ret, i, k, step, l;
     325             : 
     326           0 :     ret = ff_request_frame(ctx->inputs[0]);
     327             : 
     328           0 :     if (s->slide == 4 && ret == AVERROR_EOF && s->nb_values > 0) {
     329           0 :         s->x = l = 0;
     330           0 :         step = ceil(s->nb_values / (float)s->w);
     331             : 
     332           0 :         for (k = 0; k < s->nb_values; k++) {
     333           0 :             for (i = 0; i < 4; i++) {
     334             :                 double values[VAR_VARS_NB];
     335             :                 int j, y, x, old;
     336             :                 uint32_t fg, bg;
     337           0 :                 float vf = s->values[i][k];
     338             : 
     339           0 :                 if (isnan(vf))
     340           0 :                     continue;
     341             : 
     342           0 :                 values[VAR_MIN] = s->min;
     343           0 :                 values[VAR_MAX] = s->max;
     344           0 :                 values[VAR_VAL] = vf;
     345             : 
     346           0 :                 fg = av_expr_eval(s->fg_expr[i], values, NULL);
     347           0 :                 bg = AV_RN32(s->bg);
     348             : 
     349           0 :                 x = s->x;
     350           0 :                 y = (outlink->h - 1) * (1 - ((vf - s->min) / (s->max - s->min)));
     351             : 
     352           0 :                 switch (s->mode) {
     353           0 :                 case 0:
     354           0 :                     old = AV_RN32(out->data[0] + y * out->linesize[0] + x * 4);
     355           0 :                     for (j = y; j < outlink->h; j++) {
     356           0 :                         if (old != bg &&
     357           0 :                             (AV_RN32(out->data[0] + j * out->linesize[0] + x * 4) != old) ||
     358           0 :                             AV_RN32(out->data[0] + FFMIN(j+1, outlink->h - 1) * out->linesize[0] + x * 4) != old) {
     359           0 :                             draw_dot(fg, x, j, out);
     360           0 :                             break;
     361             :                         }
     362           0 :                         draw_dot(fg, x, j, out);
     363             :                     }
     364           0 :                     break;
     365           0 :                 case 1:
     366           0 :                     draw_dot(fg, x, y, out);
     367           0 :                     break;
     368           0 :                 case 2:
     369           0 :                     if (s->first) {
     370           0 :                         s->first = 0;
     371           0 :                         s->prev_y[i] = y;
     372             :                     }
     373             : 
     374           0 :                     if (y <= s->prev_y[i]) {
     375           0 :                         for (j = y; j <= s->prev_y[i]; j++)
     376           0 :                             draw_dot(fg, x, j, out);
     377             :                     } else {
     378           0 :                         for (j = s->prev_y[i]; j <= y; j++)
     379           0 :                             draw_dot(fg, x, j, out);
     380             :                     }
     381           0 :                     s->prev_y[i] = y;
     382           0 :                     break;
     383             :                 }
     384             :             }
     385             : 
     386           0 :             l++;
     387           0 :             if (l >= step) {
     388           0 :                 l = 0;
     389           0 :                 s->x++;
     390             :             }
     391             :         }
     392             : 
     393           0 :         s->nb_values = 0;
     394           0 :         out->pts = 0;
     395           0 :         ret = ff_filter_frame(ctx->outputs[0], s->out);
     396             :     }
     397             : 
     398           0 :     return ret;
     399             : }
     400             : 
     401           0 : static int config_output(AVFilterLink *outlink)
     402             : {
     403           0 :     DrawGraphContext *s = outlink->src->priv;
     404             : 
     405           0 :     outlink->w = s->w;
     406           0 :     outlink->h = s->h;
     407           0 :     outlink->sample_aspect_ratio = (AVRational){1,1};
     408             : 
     409           0 :     return 0;
     410             : }
     411             : 
     412           0 : static av_cold void uninit(AVFilterContext *ctx)
     413             : {
     414           0 :     DrawGraphContext *s = ctx->priv;
     415             :     int i;
     416             : 
     417           0 :     for (i = 0; i < 4; i++)
     418           0 :         av_expr_free(s->fg_expr[i]);
     419             : 
     420           0 :     if (s->slide != 4)
     421           0 :         av_frame_free(&s->out);
     422             : 
     423           0 :     av_freep(&s->values[0]);
     424           0 :     av_freep(&s->values[1]);
     425           0 :     av_freep(&s->values[2]);
     426           0 :     av_freep(&s->values[3]);
     427           0 : }
     428             : 
     429             : #if CONFIG_DRAWGRAPH_FILTER
     430             : 
     431             : AVFILTER_DEFINE_CLASS(drawgraph);
     432             : 
     433             : static const AVFilterPad drawgraph_inputs[] = {
     434             :     {
     435             :         .name         = "default",
     436             :         .type         = AVMEDIA_TYPE_VIDEO,
     437             :         .filter_frame = filter_frame,
     438             :     },
     439             :     { NULL }
     440             : };
     441             : 
     442             : static const AVFilterPad drawgraph_outputs[] = {
     443             :     {
     444             :         .name         = "default",
     445             :         .type         = AVMEDIA_TYPE_VIDEO,
     446             :         .config_props = config_output,
     447             :         .request_frame = request_frame,
     448             :     },
     449             :     { NULL }
     450             : };
     451             : 
     452             : AVFilter ff_vf_drawgraph = {
     453             :     .name          = "drawgraph",
     454             :     .description   = NULL_IF_CONFIG_SMALL("Draw a graph using input video metadata."),
     455             :     .priv_size     = sizeof(DrawGraphContext),
     456             :     .priv_class    = &drawgraph_class,
     457             :     .query_formats = query_formats,
     458             :     .init          = init,
     459             :     .uninit        = uninit,
     460             :     .inputs        = drawgraph_inputs,
     461             :     .outputs       = drawgraph_outputs,
     462             : };
     463             : 
     464             : #endif // CONFIG_DRAWGRAPH_FILTER
     465             : 
     466             : #if CONFIG_ADRAWGRAPH_FILTER
     467             : 
     468             : #define adrawgraph_options drawgraph_options
     469             : AVFILTER_DEFINE_CLASS(adrawgraph);
     470             : 
     471             : static const AVFilterPad adrawgraph_inputs[] = {
     472             :     {
     473             :         .name         = "default",
     474             :         .type         = AVMEDIA_TYPE_AUDIO,
     475             :         .filter_frame = filter_frame,
     476             :     },
     477             :     { NULL }
     478             : };
     479             : 
     480             : static const AVFilterPad adrawgraph_outputs[] = {
     481             :     {
     482             :         .name         = "default",
     483             :         .type         = AVMEDIA_TYPE_VIDEO,
     484             :         .config_props = config_output,
     485             :         .request_frame = request_frame,
     486             :     },
     487             :     { NULL }
     488             : };
     489             : 
     490             : AVFilter ff_avf_adrawgraph = {
     491             :     .name          = "adrawgraph",
     492             :     .description   = NULL_IF_CONFIG_SMALL("Draw a graph using input audio metadata."),
     493             :     .priv_size     = sizeof(DrawGraphContext),
     494             :     .priv_class    = &adrawgraph_class,
     495             :     .query_formats = query_formats,
     496             :     .init          = init,
     497             :     .uninit        = uninit,
     498             :     .inputs        = adrawgraph_inputs,
     499             :     .outputs       = adrawgraph_outputs,
     500             : };
     501             : #endif // CONFIG_ADRAWGRAPH_FILTER

Generated by: LCOV version 1.13