ffmpeg怎么样处理网络流
http://blog.sina.com.cn/s/blog_675142dc01010otk.html
最近遇到好几个人在问ffmpeg如何处理网络流,刚好前段时间也在做这方面,抽空整理了下,把主要代码发出来,希望对大家有用。为简单处理,我这里只简单介绍UDP接收TS流,其实只要是socket接收的都可以类似处理。
#include "utils.h"
#include <pthread.h>
#include <libavcodec/avcodec.h>
#include <libavformat/avformat.h>
UdpQueue recvqueue;
UdpParam udpParam;
//注册av_read_frame的回调函数,这里只是最简处理,实际应用中应加上出错处理,超时等待...
int read_data(void *opaque, uint8_t *buf, int buf_size) {
int size = buf_size;
int ret;
// printf("read data %d\n", buf_size);
do {
ret = get_queue(&recvqueue, buf, buf_size);
} while (ret);
// printf("read data Ok %d\n", buf_size);
return size;
}
#define BUF_SIZE 4096*500
int main(int argc, char** argv) {
init_queue(&recvqueue, 1024*500);
udpParam.argv = argv;
udpParam.queue = &recvqueue;
uint8_t *buf = av_mallocz(sizeof(uint8_t)*BUF_SIZE);
//UDP接收线程
pthread_t udp_recv_thread;
pthread_create(&udp_recv_thread, NULL, udp_ts_recv,
&udpParam);
pthread_detach(udp_recv_thread);
av_register_all();
AVCodec *pVideoCodec, *pAudioCodec;
AVCodecContext *pVideoCodecCtx = NULL;
AVCodecContext *pAudioCodecCtx = NULL;
AVIOContext * pb = NULL;
AVInputFormat *piFmt = NULL;
AVFormatContext *pFmt = NULL;
//step1:申请一个AVIOContext
pb = avio_alloc_context(buf, BUF_SIZE, 0, NULL, read_data, NULL,
NULL);
if (!pb) {
fprintf(stderr, "avio alloc failed!\n");
return -1;
}
//step2:探测流格式
if (av_probe_input_buffer(pb, &piFmt, "", NULL, 0,
0) < 0) {
fprintf(stderr, "probe failed!\n");
return -1;
} else {
fprintf(stdout, "probe success!\n");
fprintf(stdout, "format: %s[%s]\n", piFmt->name,
piFmt->long_name);
}
pFmt = avformat_alloc_context();
pFmt->pb = pb; //step3:这一步很关键
//step4:打开流
if (avformat_open_input(&pFmt, "", piFmt, NULL)
< 0) {
fprintf(stderr, "avformat open failed.\n");
return -1;
} else {
fprintf(stdout, "open stream success!\n");
}
//以下就和文件处理一致了
if (av_find_stream_info(pFmt) < 0) {
fprintf(stderr, "could not fine stream.\n");
return -1;
}
av_dump_format(pFmt, 0, "", 0);
int videoindex = -1;
int audioindex = -1;
for (int i = 0; i < pFmt->nb_streams;
i++) {
if (
(pFmt->streams[i]->codec->codec_type
== AVMEDIA_TYPE_VIDEO) &&
(videoindex < 0) ) {
videoindex = i;
}
if (
(pFmt->streams[i]->codec->codec_type
== AVMEDIA_TYPE_AUDIO) &&
(audioindex < 0) ) {
audioindex = i;
}
}
if (videoindex < 0 || audioindex <
0) {
fprintf(stderr, "videoindex=%d, audioindex=%d\n", videoindex,
audioindex);
return -1;
}
AVStream *pVst,*pAst;
pVst = pFmt->streams[videoindex];
pAst = pFmt->streams[audioindex];
pVideoCodecCtx = pVst->codec;
pAudioCodecCtx = pAst->codec;
pVideoCodec =
avcodec_find_decoder(pVideoCodecCtx->codec_id);
if (!pVideoCodec) {
fprintf(stderr, "could not find video decoder!\n");
return -1;
}
if (avcodec_open(pVideoCodecCtx, pVideoCodec) < 0)
{
fprintf(stderr, "could not open video codec!\n");
return -1;
}
pAudioCodec =
avcodec_find_decoder(pAudioCodecCtx->codec_id);
if (!pAudioCodec) {
fprintf(stderr, "could not find audio decoder!\n");
return -1;
}
if (avcodec_open(pAudioCodecCtx, pAudioCodec) < 0)
{
fprintf(stderr, "could not open audio codec!\n");
return -1;
}
int got_picture;
uint8_t samples[AVCODEC_MAX_AUDIO_FRAME_SIZE*3/2];
AVFrame *pframe = avcodec_alloc_frame();
AVPacket pkt;
av_init_packet(&pkt);
while(1) {
if (av_read_frame(pFmt, &pkt) >= 0)
{
if (pkt.stream_index == videoindex) {
fprintf(stdout, "pkt.size=%d,pkt.pts=%lld, pkt.data=0x%x.",
pkt.size, pkt.pts,(unsigned int)pkt.data);
avcodec_decode_video2(pVideoCodecCtx, pframe,
&got_picture, &pkt);
if (got_picture) {
fprintf(stdout, "decode one video frame!\n");
}
}else if (pkt.stream_index == audioindex) {
int frame_size = AVCODEC_MAX_AUDIO_FRAME_SIZE*3/2;
if (avcodec_decode_audio3(pAudioCodecCtx, (int16_t *)samples,
&frame_size, &pkt)
>= 0) {
fprintf(stdout, "decode one audio frame!\n");
}
}
av_free_packet(&pkt);
}
}
av_free(buf);
av_free(pframe);
free_queue(&recvqueue);
return 0;
}
ffmpeg怎么样处理网络流的更多相关文章
- FFmpeg 如何探测网络流格式/如何从内存中获取数据
文章转自:http://blog.csdn.net/rootusers/article/details/42551935 一般ffmpeg都是直接从文件中读取或者从网络流中读取,比如rtp://xx. ...
- FFmpeg开发笔记(九):ffmpeg解码rtsp流并使用SDL同步播放
前言 ffmpeg播放rtsp网络流和摄像头流. Demo 使用ffmpeg播放局域网rtsp1080p海康摄像头:延迟0.2s,存在马赛克 使用ffmpeg播放网络rtsp文件流 ...
- 可用的rtmp互联网地址
rtmp://live.hkstv.hk.lxdns.com/live/hks 测试可用. vlc使用ffmpeg取rtmp网络流. 代码文件路径: vlc-2.2.1\modules\access\ ...
- ffmpeg处理网络流
最近遇到好几个人在问ffmpeg如何处理网络流,刚好前段时间也在做这方面,抽空整理了下,把主要代码发出来,希望对大家有用.为简单处理,我这里只简单介绍UDP接收TS流,其实只要是socket接收的都可 ...
- live555+ffmpeg如何提取关键帧(I帧,P帧,B帧)
live555+ffmpeg如何提取关键帧(I帧,P帧,B帧)开发流媒体播放器的时候,特别是在windows mobile,symbian(S60)平台开发时,很可能遇到需要自己开发播放器的情况.S ...
- ffmpeg入门
总入口 http://blog.csdn.net/leixiaohua1020/article/details/15811977 各结构体介绍 http://blog.csdn.net/leixiao ...
- 最简单的基于FFmpeg的推流器(以推送RTMP为例)
===================================================== 最简单的基于FFmpeg的推流器系列文章列表: <最简单的基于FFmpeg的推流器(以 ...
- 基于ffmpeg网络播放器的教程与总结
基于ffmpeg网络播放器的教程与总结 一. 概述 为了解决在线无广告播放youku网上的视频.(youku把每个视频切换成若干个小视频). 视频资源解析可以从www.flvcd. ...
- Ffmpeg 视频教程
最近一段时间找时间录制了一些Ffmpeg视频教程,还有录制完毕,会持续更新,内容会包含Ffmeg保存文件,网络流转发, 编码,解码,播放器制作,以及服务端搭建等等,适合初学者,有需要的朋友的可以关注: ...
随机推荐
- 【转】Python高级特性——切片(Slice)
摘录廖雪峰网站 定义一个list: 1 L = ['haha','xixi','hehe','heihei','gaga'] 取其前三个元素: >>> L[0],L[1],L[2] ...
- START法则
用途:在做项目总结以及阶段性报告等的时候,可以很好的帮自己对整个工作过程进行梳理和总结,很好的表现出自己分析问题的清晰性.条理性和逻辑性. 定义:STAR法则是情境(situation).任务(tas ...
- Java 生产者消费者 & 例题
Queue http://m635674608.iteye.com/blog/1739860 http://www.iteye.com/problems/84758 http://blog.csdn. ...
- 破解 apk
韩梦飞沙 yue31313 韩亚飞 han_meng_fei_sha 313134555@qq.com 使用 ida pro 直接分析 apk . 有些代码 混淆 处理过, 就需要 动态调试 辅助 ...
- 【bzoj2190】[SDOI2008]仪仗队 数论 欧拉函数 筛法
http://www.lydsy.com/JudgeOnline/problem.php?id=2190 裸欧拉函数,先不计算对角线(a,a)的一列,然后算出1到n-1的所有欧拉函数相加*2,再加 ...
- 十一. 图形、图像与多媒体4.Graphics类的绘图方法
Graphics类提供基本绘图方法,Graphics2D类提供更强大的绘图能力.本节讲解Graphics类,下节讲解Graphics2D. Graphics类提供基本的几何图形绘制方法,主要有:画线段 ...
- 防止xss攻击
<?php function _removeXSS($val) { $search = 'abcdefghijklmnopqrstuvwxyz'; $search .= 'ABCDEFGHIJK ...
- JNI小试牛刀
JNI: JNI是Java Native Interface的缩写,它提供了若干的API实现了Java和其他语言的通信(主要是C&C++).从Java1.1开始,JNI标准成为java平台的一 ...
- 新浪微博(t.sina)简单授权代码及API测试
http://www.eoeandroid.com/thread-53701-1-1.html package mobson.weiboku.view; import java.util.ArrayL ...
- 你家的Wifi密码安全吗?
WiFi在给我们提供方便的无线网络同时,也带了一些隐患.如果对WiFi不设密码的话,一来会因为蹭网而影响网速,二来给信息安全带来了不小隐患.针对WiFi的安全手段,一般来说就是加密.最初的加密方式是W ...