OSDN Git Service

d5ad518c71af4b256b5d67e213cbcb41b9a89372
[android-x86/external-stagefright-plugins.git] / utils / ffmpeg_utils.cpp
1 /*
2  * Copyright 2012 Michael Chen <omxcodec@gmail.com>
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #define LOG_NDEBUG 0
17 #define LOG_TAG "FFMPEG"
18 #include <utils/Log.h>
19
20 #include <utils/Errors.h>
21
22 #ifdef __cplusplus
23 extern "C" {
24 #endif
25
26 #include "config.h"
27
28 #include <unistd.h>
29 #include <stdlib.h>
30 #include <inttypes.h>
31 #include <math.h>
32 #include <limits.h> /* INT_MAX */
33
34 #include "libavutil/avstring.h"
35 #include "libavutil/colorspace.h"
36 #include "libavutil/mathematics.h"
37 #include "libavutil/pixdesc.h"
38 #include "libavutil/imgutils.h"
39 #include "libavutil/dict.h"
40 #include "libavutil/parseutils.h"
41 #include "libavutil/samplefmt.h"
42 #include "libavutil/avassert.h"
43 #include "libavutil/intreadwrite.h"
44 #include "libavformat/avformat.h"
45 #include "libavdevice/avdevice.h"
46 #include "libswscale/swscale.h"
47 #include "libavcodec/audioconvert.h"
48 #include "libavutil/opt.h"
49 #include "libavutil/internal.h"
50 #include "libavcodec/avfft.h"
51 #include "libswresample/swresample.h"
52
53 #include "cmdutils.h"
54
55 #undef strncpy
56 #include <string.h>
57
58 #ifdef __cplusplus
59 }
60 #endif
61
62 #include <cutils/properties.h>
63
64 #include "ffmpeg_utils.h"
65 #include "ffmpeg_source.h"
66
67 // log
68 static int flags;
69
70 // dummy
71 const char program_name[] = "dummy";
72 const int program_birth_year = 2012;
73
74 // init ffmpeg
75 static pthread_mutex_t init_mutex = PTHREAD_MUTEX_INITIALIZER;
76 static int ref_count = 0;
77
78 namespace android {
79
80 //////////////////////////////////////////////////////////////////////////////////
81 // dummy
82 //////////////////////////////////////////////////////////////////////////////////
83 #ifdef __cplusplus
84 extern "C" {
85 #endif
86
87 void av_noreturn exit_program(int ret)
88 {
89     // do nothing
90 }
91
92 void show_help_default(const char *opt, const char *arg)
93 {
94     // do nothing
95 }
96
97 #ifdef __cplusplus
98 }
99 #endif
100
101 //////////////////////////////////////////////////////////////////////////////////
102 // log
103 //////////////////////////////////////////////////////////////////////////////////
104 static void sanitize(uint8_t *line){
105     while(*line){
106         if(*line < 0x08 || (*line > 0x0D && *line < 0x20))
107             *line='?';
108         line++;
109     }
110 }
111
112 // TODO, remove static variables to support multi-instances
113 void nam_av_log_callback(void* ptr, int level, const char* fmt, va_list vl)
114 {
115     static int print_prefix = 1;
116     static int count;
117     static char prev[1024];
118     char line[1024];
119     static int is_atty;
120
121     if (level > av_log_get_level())
122         return;
123     av_log_format_line(ptr, level, fmt, vl, line, sizeof(line), &print_prefix);
124
125     if (print_prefix && (flags & AV_LOG_SKIP_REPEATED) && !strcmp(line, prev)){
126         count++;
127         return;
128     }
129     if (count > 0) {
130         LOGI("Last message repeated %d times\n", count);
131         count = 0;
132     }
133     strcpy(prev, line);
134     sanitize((uint8_t *)line);
135
136 #if 0
137     LOGI("%s", line);
138 #else
139 #define LOG_BUF_SIZE 1024
140     static char g_msg[LOG_BUF_SIZE];
141     static int g_msg_len = 0;
142
143     int saw_lf, check_len;
144
145     do {
146         check_len = g_msg_len + strlen(line) + 1;
147         if (check_len <= LOG_BUF_SIZE) {
148             /* lf: Line feed ('\n') */
149             saw_lf = (strchr(line, '\n') != NULL) ? 1 : 0;
150             strncpy(g_msg + g_msg_len, line, strlen(line));
151             g_msg_len += strlen(line);
152             if (!saw_lf) {
153                /* skip */
154                return;
155             } else {
156                /* attach the line feed */
157                g_msg_len += 1;
158                g_msg[g_msg_len] = '\n';
159             }
160         } else {
161             /* trace is fragmented */
162             g_msg_len += 1;
163             g_msg[g_msg_len] = '\n';
164         }
165         LOGI("%s", g_msg);
166         /* reset g_msg and g_msg_len */
167         memset(g_msg, 0, LOG_BUF_SIZE);
168         g_msg_len = 0;
169      } while (check_len > LOG_BUF_SIZE);
170 #endif
171 }
172
173 void nam_av_log_set_flags(int arg)
174 {
175     flags = arg;
176 }
177
178 #if 0
179 const struct { const char *name; int level; } log_levels[] = {
180     { "quiet"  , AV_LOG_QUIET   },
181     { "panic"  , AV_LOG_PANIC   },
182     { "fatal"  , AV_LOG_FATAL   },
183     { "error"  , AV_LOG_ERROR   },
184     { "warning", AV_LOG_WARNING },
185     { "info"   , AV_LOG_INFO    },
186     { "verbose", AV_LOG_VERBOSE },
187     { "debug"  , AV_LOG_DEBUG   },
188 };
189
190 #define AV_LOG_QUIET    -8
191 #define AV_LOG_PANIC     0
192 #define AV_LOG_FATAL     8
193 #define AV_LOG_ERROR    16
194 #define AV_LOG_WARNING  24
195 #define AV_LOG_INFO     32
196 #define AV_LOG_VERBOSE  40
197 #define AV_LOG_DEBUG    48
198 #endif
199
200 //////////////////////////////////////////////////////////////////////////////////
201 // constructor and destructor
202 //////////////////////////////////////////////////////////////////////////////////
203 /* Mutex manager callback. */
204 static int lockmgr(void **mtx, enum AVLockOp op)
205 {
206     switch (op) {
207     case AV_LOCK_CREATE:
208         *mtx = (void *)av_malloc(sizeof(pthread_mutex_t));
209         if (!*mtx)
210             return 1;
211         return !!pthread_mutex_init((pthread_mutex_t *)(*mtx), NULL);
212     case AV_LOCK_OBTAIN:
213         return !!pthread_mutex_lock((pthread_mutex_t *)(*mtx));
214     case AV_LOCK_RELEASE:
215         return !!pthread_mutex_unlock((pthread_mutex_t *)(*mtx));
216     case AV_LOCK_DESTROY:
217         pthread_mutex_destroy((pthread_mutex_t *)(*mtx));
218         av_freep(mtx);
219         return 0;
220     }
221     return 1;
222 }
223
224 /**
225  * To debug ffmpeg", type this command on the console before starting playback:
226  *     setprop debug.nam.ffmpeg 1
227  * To disable the debug, type:
228  *     setprop debug.nam.ffmpge 0
229 */
230 status_t initFFmpeg() 
231 {
232     status_t ret = OK;
233     bool debug_enabled = false;
234     char value[PROPERTY_VALUE_MAX];
235
236     pthread_mutex_lock(&init_mutex);
237
238     if (property_get("debug.nam.ffmpeg", value, NULL)
239         && (!strcmp(value, "1") || !av_strcasecmp(value, "true"))) {
240         LOGI("set ffmpeg debug level to AV_LOG_DEBUG");
241         debug_enabled = true;
242     }
243     if (debug_enabled)
244         av_log_set_level(AV_LOG_DEBUG);
245     else
246         av_log_set_level(AV_LOG_INFO);
247
248     if(ref_count == 0) {
249         nam_av_log_set_flags(AV_LOG_SKIP_REPEATED);
250         av_log_set_callback(nam_av_log_callback);
251
252         /* register all codecs, demux and protocols */
253         avcodec_register_all();
254 #if CONFIG_AVDEVICE
255         avdevice_register_all();
256 #endif
257         av_register_all();
258         avformat_network_init();
259
260         /* register android source */
261         ffmpeg_register_android_source();
262
263         init_opts();
264
265         if (av_lockmgr_register(lockmgr)) {
266             LOGE("could not initialize lock manager!");
267             ret = NO_INIT;
268         }
269     }
270
271     // update counter
272     ref_count++;
273
274     pthread_mutex_unlock(&init_mutex);
275
276     return ret;
277 }
278
279 void deInitFFmpeg()
280 {
281     pthread_mutex_lock(&init_mutex);
282
283     // update counter
284     ref_count--;
285
286     if(ref_count == 0) {
287         av_lockmgr_register(NULL);
288         uninit_opts();
289         avformat_network_deinit();
290     }
291
292     pthread_mutex_unlock(&init_mutex);
293 }
294
295 //////////////////////////////////////////////////////////////////////////////////
296 // parser
297 //////////////////////////////////////////////////////////////////////////////////
298 /* H.264 bitstream with start codes, NOT AVC1! ref: libavcodec/h264_parser.c */
299 static int h264_split(AVCodecContext *avctx,
300                       const uint8_t *buf, int buf_size, int check_compatible_only)
301 {
302     int i;
303     uint32_t state = -1;
304     int has_sps= 0;
305     int has_pps= 0;
306
307     //av_hex_dump(stderr, buf, 100);
308
309     for(i=0; i<=buf_size; i++){
310         if((state&0xFFFFFF1F) == 0x107) {
311             LOGI("found NAL_SPS");
312             has_sps=1;
313         }
314         if((state&0xFFFFFF1F) == 0x108) {
315             LOGI("found NAL_PPS");
316             has_pps=1;
317             if (check_compatible_only)
318                 return (has_sps & has_pps);
319         }
320         if((state&0xFFFFFF00) == 0x100 && ((state&0xFFFFFF1F) == 0x101 || (state&0xFFFFFF1F) == 0x102 || (state&0xFFFFFF1F) == 0x105)){
321             if(has_pps){
322                 while(i>4 && buf[i-5]==0) i--;
323                 return i-4;
324             }
325         }
326         if (i<buf_size)
327             state= (state<<8) | buf[i];
328     }
329     return 0;
330 }
331
332 /* ref: libavcodec/mpegvideo_parser.c */
333 static int mpegvideo_split(AVCodecContext *avctx,
334                            const uint8_t *buf, int buf_size, int check_compatible_only)
335 {
336     int i;
337     uint32_t state= -1;
338     int found=0;
339
340     for(i=0; i<buf_size; i++){
341         state= (state<<8) | buf[i];
342         if(state == 0x1B3){
343             found=1;
344         }else if(found && state != 0x1B5 && state < 0x200 && state >= 0x100)
345             return i-3;
346     }
347     return 0;
348 }
349
350 /* split extradata from buf for Android OMXCodec */
351 int parser_split(AVCodecContext *avctx,
352                       const uint8_t *buf, int buf_size)
353 {
354     if (!avctx || !buf || buf_size <= 0) {
355         LOGE("parser split, valid params");
356         return 0;
357     }
358
359     if (avctx->codec_id == CODEC_ID_H264) {
360         return h264_split(avctx, buf, buf_size, 0);
361     } else if (avctx->codec_id == CODEC_ID_MPEG2VIDEO ||
362             avctx->codec_id == CODEC_ID_MPEG4) {
363         return mpegvideo_split(avctx, buf, buf_size, 0);
364     } else {
365         LOGE("parser split, unsupport the codec, id: 0x%0x", avctx->codec_id);
366     }
367
368     return 0;
369 }
370
371 int is_extradata_compatible_with_android(AVCodecContext *avctx)
372 {
373     if (avctx->extradata_size <= 0) {
374         LOGI("extradata_size <= 0, extradata is not compatible with android decoder, the codec id: 0x%0x", avctx->codec_id);
375         return 0;
376     }
377
378     if (avctx->codec_id == CODEC_ID_H264 && avctx->extradata[0] != 1 /* configurationVersion */) {
379         // SPS + PPS
380         return !!(h264_split(avctx, avctx->extradata, avctx->extradata_size, 1) > 0);
381     } else {
382         // default, FIXME
383         return !!(avctx->extradata_size > 0);
384     }
385 }
386
387 }  // namespace android
388