aomstats.c (3114B)
1 /* 2 * Copyright (c) 2016, Alliance for Open Media. All rights reserved. 3 * 4 * This source code is subject to the terms of the BSD 2 Clause License and 5 * the Alliance for Open Media Patent License 1.0. If the BSD 2 Clause License 6 * was not distributed with this source code in the LICENSE file, you can 7 * obtain it at www.aomedia.org/license/software. If the Alliance for Open 8 * Media Patent License 1.0 was not distributed with this source code in the 9 * PATENTS file, you can obtain it at www.aomedia.org/license/patent. 10 */ 11 12 #include "stats/aomstats.h" 13 14 #include <assert.h> 15 #include <math.h> 16 #include <stdlib.h> 17 #include <string.h> 18 19 #include "aom_dsp/aom_dsp_common.h" 20 #include "common/tools_common.h" 21 22 int stats_open_file(stats_io_t *stats, const char *fpf, int pass) { 23 int res; 24 stats->pass = pass; 25 26 if (pass == 0) { 27 stats->file = fopen(fpf, "wb"); 28 stats->buf.sz = 0; 29 stats->buf.buf = NULL; 30 res = (stats->file != NULL); 31 } else { 32 size_t nbytes; 33 34 stats->file = fopen(fpf, "rb"); 35 36 if (stats->file == NULL) fatal("First-pass stats file does not exist!"); 37 38 if (fseek(stats->file, 0, SEEK_END)) 39 fatal("First-pass stats file must be seekable!"); 40 41 stats->buf.sz = stats->buf_alloc_sz = ftell(stats->file); 42 rewind(stats->file); 43 44 stats->buf.buf = malloc(stats->buf_alloc_sz); 45 46 if (!stats->buf.buf) 47 fatal("Failed to allocate first-pass stats buffer (%u bytes)", 48 (unsigned int)stats->buf_alloc_sz); 49 50 nbytes = fread(stats->buf.buf, 1, stats->buf.sz, stats->file); 51 res = (nbytes == stats->buf.sz); 52 } 53 54 return res; 55 } 56 57 int stats_open_mem(stats_io_t *stats, int pass) { 58 int res; 59 stats->pass = pass; 60 61 if (!pass) { 62 stats->buf.sz = 0; 63 stats->buf_alloc_sz = 64 * 1024; 64 stats->buf.buf = malloc(stats->buf_alloc_sz); 65 } 66 67 stats->buf_ptr = stats->buf.buf; 68 res = (stats->buf.buf != NULL); 69 return res; 70 } 71 72 void stats_close(stats_io_t *stats, int last_pass) { 73 if (stats->file) { 74 if (stats->pass == last_pass) { 75 free(stats->buf.buf); 76 } 77 78 fclose(stats->file); 79 stats->file = NULL; 80 } else { 81 if (stats->pass == last_pass) free(stats->buf.buf); 82 } 83 } 84 85 void stats_write(stats_io_t *stats, const void *pkt, size_t len) { 86 if (stats->file) { 87 (void)fwrite(pkt, 1, len, stats->file); 88 return; 89 } 90 assert(stats->buf.sz <= stats->buf_alloc_sz); 91 assert(0 < stats->buf_alloc_sz); 92 if (stats->buf.sz + len > stats->buf_alloc_sz) { 93 // Grow by a factor of 1.5 each time, for amortized constant time. 94 // Also make sure there is enough room for the data. 95 size_t new_sz = AOMMAX((3 * stats->buf_alloc_sz) / 2, stats->buf.sz + len); 96 char *new_ptr = realloc(stats->buf.buf, new_sz); 97 98 if (new_ptr) { 99 stats->buf_ptr = new_ptr + (stats->buf_ptr - (char *)stats->buf.buf); 100 stats->buf.buf = new_ptr; 101 stats->buf_alloc_sz = new_sz; 102 } else { 103 fatal("Failed to realloc firstpass stats buffer."); 104 } 105 } 106 107 memcpy(stats->buf_ptr, pkt, len); 108 stats->buf.sz += len; 109 stats->buf_ptr += len; 110 } 111 112 aom_fixed_buf_t stats_get(stats_io_t *stats) { return stats->buf; }