]> granicus.if.org Git - libvpx/blob - tools_common.c
Merge "Cleaning up update_stats() function."
[libvpx] / tools_common.c
1 /*
2  *  Copyright (c) 2010 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 "tools_common.h"
12
13 #include <stdarg.h>
14 #include <stdio.h>
15 #include <stdlib.h>
16 #include <string.h>
17
18 #if CONFIG_VP8_DECODER || CONFIG_VP9_DECODER
19 #include "vpx/vp8dx.h"
20 #endif
21
22 #if defined(_WIN32) || defined(__OS2__)
23 #include <io.h>
24 #include <fcntl.h>
25
26 #ifdef __OS2__
27 #define _setmode    setmode
28 #define _fileno     fileno
29 #define _O_BINARY   O_BINARY
30 #endif
31 #endif
32
33 #define LOG_ERROR(label) do {\
34   const char *l = label;\
35   va_list ap;\
36   va_start(ap, fmt);\
37   if (l)\
38     fprintf(stderr, "%s: ", l);\
39   vfprintf(stderr, fmt, ap);\
40   fprintf(stderr, "\n");\
41   va_end(ap);\
42 } while (0)
43
44
45 FILE *set_binary_mode(FILE *stream) {
46   (void)stream;
47 #if defined(_WIN32) || defined(__OS2__)
48   _setmode(_fileno(stream), _O_BINARY);
49 #endif
50   return stream;
51 }
52
53 void die(const char *fmt, ...) {
54   LOG_ERROR(NULL);
55   usage_exit();
56 }
57
58 void fatal(const char *fmt, ...) {
59   LOG_ERROR("Fatal");
60   exit(EXIT_FAILURE);
61 }
62
63 void warn(const char *fmt, ...) {
64   LOG_ERROR("Warning");
65 }
66
67 void die_codec(vpx_codec_ctx_t *ctx, const char *s) {
68   const char *detail = vpx_codec_error_detail(ctx);
69
70   printf("%s: %s\n", s, vpx_codec_error(ctx));
71   if (detail)
72     printf("    %s\n", detail);
73   exit(EXIT_FAILURE);
74 }
75
76 uint16_t mem_get_le16(const void *data) {
77   uint16_t val;
78   const uint8_t *mem = (const uint8_t*)data;
79
80   val = mem[1] << 8;
81   val |= mem[0];
82   return val;
83 }
84
85 uint32_t mem_get_le32(const void *data) {
86   uint32_t val;
87   const uint8_t *mem = (const uint8_t*)data;
88
89   val = mem[3] << 24;
90   val |= mem[2] << 16;
91   val |= mem[1] << 8;
92   val |= mem[0];
93   return val;
94 }
95
96 int read_yuv_frame(struct VpxInputContext *input_ctx, vpx_image_t *yuv_frame) {
97   FILE *f = input_ctx->file;
98   struct FileTypeDetectionBuffer *detect = &input_ctx->detect;
99   int plane = 0;
100   int shortread = 0;
101
102   for (plane = 0; plane < 3; ++plane) {
103     uint8_t *ptr;
104     const int w = (plane ? (1 + yuv_frame->d_w) / 2 : yuv_frame->d_w);
105     const int h = (plane ? (1 + yuv_frame->d_h) / 2 : yuv_frame->d_h);
106     int r;
107
108     /* Determine the correct plane based on the image format. The for-loop
109      * always counts in Y,U,V order, but this may not match the order of
110      * the data on disk.
111      */
112     switch (plane) {
113       case 1:
114         ptr = yuv_frame->planes[
115             yuv_frame->fmt == VPX_IMG_FMT_YV12 ? VPX_PLANE_V : VPX_PLANE_U];
116         break;
117       case 2:
118         ptr = yuv_frame->planes[
119             yuv_frame->fmt == VPX_IMG_FMT_YV12 ? VPX_PLANE_U : VPX_PLANE_V];
120         break;
121       default:
122         ptr = yuv_frame->planes[plane];
123     }
124
125     for (r = 0; r < h; ++r) {
126       size_t needed = w;
127       size_t buf_position = 0;
128       const size_t left = detect->buf_read - detect->position;
129       if (left > 0) {
130         const size_t more = (left < needed) ? left : needed;
131         memcpy(ptr, detect->buf + detect->position, more);
132         buf_position = more;
133         needed -= more;
134         detect->position += more;
135       }
136       if (needed > 0) {
137         shortread |= (fread(ptr + buf_position, 1, needed, f) < needed);
138       }
139
140       ptr += yuv_frame->stride[plane];
141     }
142   }
143
144   return shortread;
145 }
146
147 vpx_codec_iface_t *get_codec_interface(unsigned int fourcc) {
148   switch (fourcc) {
149 #if CONFIG_VP8_DECODER
150     case VP8_FOURCC:
151       return vpx_codec_vp8_dx();
152 #endif
153 #if CONFIG_VP9_DECODER
154     case VP9_FOURCC:
155       return vpx_codec_vp9_dx();
156 #endif
157     default:
158       return NULL;
159   }
160   return NULL;
161 }
162
163 void vpx_img_write(const vpx_image_t *img, FILE *file) {
164   int plane, y;
165
166   for (plane = 0; plane < 3; ++plane) {
167     const unsigned char *buf = img->planes[plane];
168     const int stride = img->stride[plane];
169     const int w = plane ? (img->d_w + 1) >> 1 : img->d_w;
170     const int h = plane ? (img->d_h + 1) >> 1 : img->d_h;
171
172     for (y = 0; y < h; ++y) {
173       fwrite(buf, 1, w, file);
174       buf += stride;
175     }
176   }
177 }
178
179 int vpx_img_read(vpx_image_t *img, FILE *file) {
180   int plane;
181
182   for (plane = 0; plane < 3; ++plane) {
183     unsigned char *buf = img->planes[plane];
184     const int stride = img->stride[plane];
185     const int w = plane ? (img->d_w + 1) >> 1 : img->d_w;
186     const int h = plane ? (img->d_h + 1) >> 1 : img->d_h;
187     int y;
188
189     for (y = 0; y < h; ++y) {
190       if (fread(buf, 1, w, file) != w)
191         return 0;
192       buf += stride;
193     }
194   }
195
196   return 1;
197 }
198