• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright (c) 2023 The WebM project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include <stdlib.h>
12 
13 #include "vpx/vpx_codec.h"
14 #include "vpx/vpx_tpl.h"
15 #include "vpx_mem/vpx_mem.h"
16 
17 #define CHECK_FPRINTF_ERROR(expr) \
18   do {                            \
19     if (expr < 0) {               \
20       return VPX_CODEC_ERROR;     \
21     }                             \
22   } while (0)
23 
24 #define CHECK_FSCANF_ERROR(expr, expected_value) \
25   do {                                           \
26     if (expr != expected_value) {                \
27       return VPX_CODEC_ERROR;                    \
28     }                                            \
29   } while (0)
30 
vpx_write_tpl_gop_stats(FILE * tpl_file,const VpxTplGopStats * tpl_gop_stats)31 vpx_codec_err_t vpx_write_tpl_gop_stats(FILE *tpl_file,
32                                         const VpxTplGopStats *tpl_gop_stats) {
33   int i;
34   if (tpl_file == NULL || tpl_gop_stats == NULL) return VPX_CODEC_INVALID_PARAM;
35   CHECK_FPRINTF_ERROR(fprintf(tpl_file, "%d\n", tpl_gop_stats->size));
36 
37   for (i = 0; i < tpl_gop_stats->size; i++) {
38     VpxTplFrameStats frame_stats = tpl_gop_stats->frame_stats_list[i];
39     const int num_blocks = frame_stats.num_blocks;
40     int block;
41     CHECK_FPRINTF_ERROR(fprintf(tpl_file, "%d %d %d\n", frame_stats.frame_width,
42                                 frame_stats.frame_height, num_blocks));
43     for (block = 0; block < num_blocks; block++) {
44       VpxTplBlockStats block_stats = frame_stats.block_stats_list[block];
45       CHECK_FPRINTF_ERROR(
46           fprintf(tpl_file,
47                   "%" PRId64 " %" PRId64 " %" PRId16 " %" PRId16 " %" PRId64
48                   " %" PRId64 " %d\n",
49                   block_stats.inter_cost, block_stats.intra_cost,
50                   block_stats.mv_c, block_stats.mv_r, block_stats.recrf_dist,
51                   block_stats.recrf_rate, block_stats.ref_frame_index));
52     }
53   }
54 
55   return VPX_CODEC_OK;
56 }
57 
vpx_read_tpl_gop_stats(FILE * tpl_file,VpxTplGopStats * tpl_gop_stats)58 vpx_codec_err_t vpx_read_tpl_gop_stats(FILE *tpl_file,
59                                        VpxTplGopStats *tpl_gop_stats) {
60   int i, frame_list_size;
61   if (tpl_file == NULL || tpl_gop_stats == NULL) return VPX_CODEC_INVALID_PARAM;
62   CHECK_FSCANF_ERROR(fscanf(tpl_file, "%d\n", &frame_list_size), 1);
63   tpl_gop_stats->size = frame_list_size;
64   tpl_gop_stats->frame_stats_list = (VpxTplFrameStats *)vpx_calloc(
65       frame_list_size, sizeof(tpl_gop_stats->frame_stats_list[0]));
66   if (tpl_gop_stats->frame_stats_list == NULL) {
67     return VPX_CODEC_MEM_ERROR;
68   }
69   for (i = 0; i < frame_list_size; i++) {
70     VpxTplFrameStats *frame_stats = &tpl_gop_stats->frame_stats_list[i];
71     int num_blocks, width, height, block;
72     CHECK_FSCANF_ERROR(
73         fscanf(tpl_file, "%d %d %d\n", &width, &height, &num_blocks), 3);
74     frame_stats->num_blocks = num_blocks;
75     frame_stats->frame_width = width;
76     frame_stats->frame_height = height;
77     frame_stats->block_stats_list = (VpxTplBlockStats *)vpx_calloc(
78         num_blocks, sizeof(frame_stats->block_stats_list[0]));
79     if (frame_stats->block_stats_list == NULL) {
80       vpx_free_tpl_gop_stats(tpl_gop_stats);
81       return VPX_CODEC_MEM_ERROR;
82     }
83     for (block = 0; block < num_blocks; block++) {
84       VpxTplBlockStats *block_stats = &frame_stats->block_stats_list[block];
85       CHECK_FSCANF_ERROR(
86           fscanf(tpl_file,
87                  "%" SCNd64 " %" SCNd64 " %" SCNd16 " %" SCNd16 " %" SCNd64
88                  " %" SCNd64 " %d\n",
89                  &block_stats->inter_cost, &block_stats->intra_cost,
90                  &block_stats->mv_c, &block_stats->mv_r,
91                  &block_stats->recrf_dist, &block_stats->recrf_rate,
92                  &block_stats->ref_frame_index),
93           7);
94     }
95   }
96 
97   return VPX_CODEC_OK;
98 }
99 
vpx_free_tpl_gop_stats(VpxTplGopStats * tpl_gop_stats)100 void vpx_free_tpl_gop_stats(VpxTplGopStats *tpl_gop_stats) {
101   int frame;
102   if (tpl_gop_stats == NULL) return;
103   for (frame = 0; frame < tpl_gop_stats->size; frame++) {
104     vpx_free(tpl_gop_stats->frame_stats_list[frame].block_stats_list);
105   }
106   vpx_free(tpl_gop_stats->frame_stats_list);
107 }
108