?? utils.c.svn-base
字號:
/* * various utility functions for use within FFmpeg * Copyright (c) 2000, 2001, 2002 Fabrice Bellard * * This file is part of FFmpeg. * * FFmpeg is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * FFmpeg is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with FFmpeg; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */#include "avformat.h"#include "libavcodec/opt.h"#include "libavutil/avstring.h"#include "riff.h"#include <sys/time.h>#include <time.h>#undef NDEBUG#include <assert.h>/** * @file libavformat/utils.c * various utility functions for use within FFmpeg */static void av_frac_init(AVFrac *f, int64_t val, int64_t num, int64_t den);static void av_frac_add(AVFrac *f, int64_t incr);/** head of registered input format linked list */AVInputFormat *first_iformat = NULL;/** head of registered output format linked list */AVOutputFormat *first_oformat = NULL;AVInputFormat *av_iformat_next(AVInputFormat *f){ if(f) return f->next; else return first_iformat;}AVOutputFormat *av_oformat_next(AVOutputFormat *f){ if(f) return f->next; else return first_oformat;}void av_register_input_format(AVInputFormat *format){ AVInputFormat **p; p = &first_iformat; while (*p != NULL) p = &(*p)->next; *p = format; format->next = NULL;}void av_register_output_format(AVOutputFormat *format){ AVOutputFormat **p; p = &first_oformat; while (*p != NULL) p = &(*p)->next; *p = format; format->next = NULL;}int match_ext(const char *filename, const char *extensions){ const char *ext, *p; char ext1[32], *q; if(!filename) return 0; ext = strrchr(filename, '.'); if (ext) { ext++; p = extensions; for(;;) { q = ext1; while (*p != '\0' && *p != ',' && q-ext1<sizeof(ext1)-1) *q++ = *p++; *q = '\0'; if (!strcasecmp(ext1, ext)) return 1; if (*p == '\0') break; p++; } } return 0;}AVOutputFormat *guess_format(const char *short_name, const char *filename, const char *mime_type){ AVOutputFormat *fmt, *fmt_found; int score_max, score; /* specific test for image sequences */#ifdef CONFIG_IMAGE2_MUXER if (!short_name && filename && av_filename_number_test(filename) && av_guess_image2_codec(filename) != CODEC_ID_NONE) { return guess_format("image2", NULL, NULL); }#endif /* Find the proper file type. */ fmt_found = NULL; score_max = 0; fmt = first_oformat; while (fmt != NULL) { score = 0; if (fmt->name && short_name && !strcmp(fmt->name, short_name)) score += 100; if (fmt->mime_type && mime_type && !strcmp(fmt->mime_type, mime_type)) score += 10; if (filename && fmt->extensions && match_ext(filename, fmt->extensions)) { score += 5; } if (score > score_max) { score_max = score; fmt_found = fmt; } fmt = fmt->next; } return fmt_found;}AVOutputFormat *guess_stream_format(const char *short_name, const char *filename, const char *mime_type){ AVOutputFormat *fmt = guess_format(short_name, filename, mime_type); if (fmt) { AVOutputFormat *stream_fmt; char stream_format_name[64]; snprintf(stream_format_name, sizeof(stream_format_name), "%s_stream", fmt->name); stream_fmt = guess_format(stream_format_name, NULL, NULL); if (stream_fmt) fmt = stream_fmt; } return fmt;}enum CodecID av_guess_codec(AVOutputFormat *fmt, const char *short_name, const char *filename, const char *mime_type, enum CodecType type){ if(type == CODEC_TYPE_VIDEO){ enum CodecID codec_id= CODEC_ID_NONE;#ifdef CONFIG_IMAGE2_MUXER if(!strcmp(fmt->name, "image2") || !strcmp(fmt->name, "image2pipe")){ codec_id= av_guess_image2_codec(filename); }#endif if(codec_id == CODEC_ID_NONE) codec_id= fmt->video_codec; return codec_id; }else if(type == CODEC_TYPE_AUDIO) return fmt->audio_codec; else return CODEC_ID_NONE;}AVInputFormat *av_find_input_format(const char *short_name){ AVInputFormat *fmt; for(fmt = first_iformat; fmt != NULL; fmt = fmt->next) { if (!strcmp(fmt->name, short_name)) return fmt; } return NULL;}/* memory handling */void av_destruct_packet(AVPacket *pkt){ av_free(pkt->data); pkt->data = NULL; pkt->size = 0;}void av_init_packet(AVPacket *pkt){ pkt->pts = AV_NOPTS_VALUE; pkt->dts = AV_NOPTS_VALUE; pkt->pos = -1; pkt->duration = 0; pkt->flags = 0; pkt->stream_index = 0; pkt->destruct= av_destruct_packet_nofree;}int av_new_packet(AVPacket *pkt, int size){ uint8_t *data; if((unsigned)size > (unsigned)size + FF_INPUT_BUFFER_PADDING_SIZE) return AVERROR(ENOMEM); data = av_malloc(size + FF_INPUT_BUFFER_PADDING_SIZE); if (!data) return AVERROR(ENOMEM); memset(data + size, 0, FF_INPUT_BUFFER_PADDING_SIZE); av_init_packet(pkt); pkt->data = data; pkt->size = size; pkt->destruct = av_destruct_packet; return 0;}int av_get_packet(ByteIOContext *s, AVPacket *pkt, int size){ int ret= av_new_packet(pkt, size); if(ret<0) return ret; pkt->pos= url_ftell(s); ret= get_buffer(s, pkt->data, size); if(ret<=0) av_free_packet(pkt); else pkt->size= ret; return ret;}int av_dup_packet(AVPacket *pkt){ if (pkt->destruct != av_destruct_packet) { uint8_t *data; /* We duplicate the packet and don't forget to add the padding again. */ if((unsigned)pkt->size > (unsigned)pkt->size + FF_INPUT_BUFFER_PADDING_SIZE) return AVERROR(ENOMEM); data = av_malloc(pkt->size + FF_INPUT_BUFFER_PADDING_SIZE); if (!data) { return AVERROR(ENOMEM); } memcpy(data, pkt->data, pkt->size); memset(data + pkt->size, 0, FF_INPUT_BUFFER_PADDING_SIZE); pkt->data = data; pkt->destruct = av_destruct_packet; } return 0;}int av_filename_number_test(const char *filename){ char buf[1024]; return filename && (av_get_frame_filename(buf, sizeof(buf), filename, 1)>=0);}static AVInputFormat *av_probe_input_format2(AVProbeData *pd, int is_opened, int *score_max){ AVInputFormat *fmt1, *fmt; int score; fmt = NULL; for(fmt1 = first_iformat; fmt1 != NULL; fmt1 = fmt1->next) { if (!is_opened == !(fmt1->flags & AVFMT_NOFILE)) continue; score = 0; if (fmt1->read_probe) { score = fmt1->read_probe(pd); } else if (fmt1->extensions) { if (match_ext(pd->filename, fmt1->extensions)) { score = 50; } } if (score > *score_max) { *score_max = score; fmt = fmt1; }else if (score == *score_max) fmt = NULL; } return fmt;}AVInputFormat *av_probe_input_format(AVProbeData *pd, int is_opened){ int score=0; return av_probe_input_format2(pd, is_opened, &score);}/************************************************************//* input media file *//** * Open a media file from an IO stream. 'fmt' must be specified. */static const char* format_to_name(void* ptr){ AVFormatContext* fc = (AVFormatContext*) ptr; if(fc->iformat) return fc->iformat->name; else if(fc->oformat) return fc->oformat->name; else return "NULL";}#define OFFSET(x) offsetof(AVFormatContext,x)#define DEFAULT 0 //should be NAN but it does not work as it is not a constant in glibc as required by ANSI/ISO C//these names are too long to be readable#define E AV_OPT_FLAG_ENCODING_PARAM#define D AV_OPT_FLAG_DECODING_PARAMstatic const AVOption options[]={{"probesize", NULL, OFFSET(probesize), FF_OPT_TYPE_INT, 32000, 32, INT_MAX, D}, /* 32000 from mpegts.c: 1.0 second at 24Mbit/s */{"muxrate", "set mux rate", OFFSET(mux_rate), FF_OPT_TYPE_INT, DEFAULT, 0, INT_MAX, E},{"packetsize", "set packet size", OFFSET(packet_size), FF_OPT_TYPE_INT, DEFAULT, 0, INT_MAX, E},{"fflags", NULL, OFFSET(flags), FF_OPT_TYPE_FLAGS, DEFAULT, INT_MIN, INT_MAX, D|E, "fflags"},{"ignidx", "ignore index", 0, FF_OPT_TYPE_CONST, AVFMT_FLAG_IGNIDX, INT_MIN, INT_MAX, D, "fflags"},{"genpts", "generate pts", 0, FF_OPT_TYPE_CONST, AVFMT_FLAG_GENPTS, INT_MIN, INT_MAX, D, "fflags"},{"track", " set the track number", OFFSET(track), FF_OPT_TYPE_INT, DEFAULT, 0, INT_MAX, E},{"year", "set the year", OFFSET(year), FF_OPT_TYPE_INT, DEFAULT, INT_MIN, INT_MAX, E},{"analyzeduration", "how many microseconds are analyzed to estimate duration", OFFSET(max_analyze_duration), FF_OPT_TYPE_INT, 3*AV_TIME_BASE, 0, INT_MAX, D},{"cryptokey", "decryption key", OFFSET(key), FF_OPT_TYPE_BINARY, 0, 0, 0, D},{"indexmem", "max memory used for timestamp index (per stream)", OFFSET(max_index_size), FF_OPT_TYPE_INT, 1<<20, 0, INT_MAX, D},{"rtbufsize", "max memory used for buffering real-time frames", OFFSET(max_picture_buffer), FF_OPT_TYPE_INT, 3041280, 0, INT_MAX, D}, /* defaults to 1s of 15fps 352x288 YUYV422 video */{"fdebug", "print specific debug info", OFFSET(debug), FF_OPT_TYPE_FLAGS, DEFAULT, 0, INT_MAX, E|D, "fdebug"},{"ts", NULL, 0, FF_OPT_TYPE_CONST, FF_FDEBUG_TS, INT_MIN, INT_MAX, E|D, "fdebug"},{NULL},};#undef E#undef D#undef DEFAULTstatic const AVClass av_format_context_class = { "AVFormatContext", format_to_name, options };static void avformat_get_context_defaults(AVFormatContext *s){ memset(s, 0, sizeof(AVFormatContext)); s->av_class = &av_format_context_class; av_opt_set_defaults(s);}AVFormatContext *av_alloc_format_context(void){ AVFormatContext *ic; ic = av_malloc(sizeof(AVFormatContext)); if (!ic) return ic; avformat_get_context_defaults(ic); ic->av_class = &av_format_context_class; return ic;}int av_open_input_stream(AVFormatContext **ic_ptr, ByteIOContext *pb, const char *filename, AVInputFormat *fmt, AVFormatParameters *ap){ int err; AVFormatContext *ic; AVFormatParameters default_ap; if(!ap){ ap=&default_ap; memset(ap, 0, sizeof(default_ap)); } if(!ap->prealloced_context) ic = av_alloc_format_context(); else ic = *ic_ptr; if (!ic) { err = AVERROR(ENOMEM); goto fail; } ic->iformat = fmt; ic->pb = pb; ic->duration = AV_NOPTS_VALUE; ic->start_time = AV_NOPTS_VALUE; av_strlcpy(ic->filename, filename, sizeof(ic->filename)); /* allocate private data */ if (fmt->priv_data_size > 0) { ic->priv_data = av_mallocz(fmt->priv_data_size); if (!ic->priv_data) { err = AVERROR(ENOMEM); goto fail; } } else { ic->priv_data = NULL; } if (ic->iformat->read_header) { err = ic->iformat->read_header(ic, ap); if (err < 0) goto fail; } if (pb && !ic->data_offset) ic->data_offset = url_ftell(ic->pb); *ic_ptr = ic; return 0; fail: if (ic) { int i; av_freep(&ic->priv_data); for(i=0;i<ic->nb_streams;i++) {
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -