FFmpeg编解码demo

            <div id="content_views" class="markdown_views prism-atom-one-dark">
                <svg xmlns="http://www.w3.org/2000/svg" style="display: none;">
                    <path stroke-linecap="round" d="M5,0 0,2.5 5,5z" id="raphael-marker-block" style="-webkit-tap-highlight-color: rgba(0, 0, 0, 0);"></path>
                </svg>
                <h2><a name="t0"></a><a id="_FFmpegDemo_0"></a>一、 FFmpeg解复用(解封装)Demo</h2> 
#include <stdio.h>
#include <libavformat/avformat.h>


int main(int argc, char **argv)
{
    //打开网络流。这里如果只需要读取本地媒体文件,不需要用到网络功能,可以不用加上这一句
//    avformat_network_init();

    const char *default_filename = "believe.mp4";

    char *in_filename = NULL;

    if(argv[1] == NULL)
    {
        in_filename = default_filename;
    }
    else
    {
        in_filename = argv[1];
    }
    printf("in_filename = %s\n", in_filename);

    //AVFormatContext是描述一个媒体文件或媒体流的构成和基本信息的结构体
    AVFormatContext *ifmt_ctx = NULL;           // 输入文件的demux

    int videoindex = -1;        // 视频索引
    int audioindex = -1;        // 音频索引


    // 打开文件,主要是探测协议类型,如果是网络文件则创建网络链接
    int ret = avformat_open_input(&ifmt_ctx, in_filename, NULL, NULL);
    if (ret < 0)  //如果打开媒体文件失败,打印失败原因
    {
        char buf[1024] = { 0 };
        av_strerror(ret, buf, sizeof(buf) - 1);
        printf("open %s failed:%s\n", in_filename, buf);
        goto failed;
    }

    ret = avformat_find_stream_info(ifmt_ctx, NULL);
    if (ret < 0)  //如果打开媒体文件失败,打印失败原因
    {
        char buf[1024] = { 0 };
        av_strerror(ret, buf, sizeof(buf) - 1);
        printf("avformat_find_stream_info %s failed:%s\n", in_filename, buf);
        goto failed;
    }

    //打开媒体文件成功
    printf_s("\n==== av_dump_format in_filename:%s ===\n", in_filename);
    av_dump_format(ifmt_ctx, 0, in_filename, 0);
    printf_s("\n==== av_dump_format finish =======\n\n");
    // url: 调用avformat_open_input读取到的媒体文件的路径/名字
    printf("media name:%s\n", ifmt_ctx->url);
    // nb_streams: nb_streams媒体流数量
    printf("stream number:%d\n", ifmt_ctx->nb_streams);
    // bit_rate: 媒体文件的码率,单位为bps
    printf("media average ratio:%lldkbps\n",(int64_t)(ifmt_ctx->bit_rate/1024));
    // 时间
    int total_seconds, hour, minute, second;
    // duration: 媒体文件时长,单位微妙
    total_seconds = (ifmt_ctx->duration) / AV_TIME_BASE;  // 1000us = 1ms, 1000ms = 1秒
    hour = total_seconds / 3600;
    minute = (total_seconds % 3600) / 60;
    second = (total_seconds % 60);
    //通过上述运算,可以得到媒体文件的总时长
    printf("total duration: %02d:%02d:%02d\n", hour, minute, second);
    printf("\n");
    /*
     * 老版本通过遍历的方式读取媒体文件视频和音频的信息
     * 新版本的FFmpeg新增加了函数av_find_best_stream,也可以取得同样的效果
     */
    for (uint32_t i = 0; i < ifmt_ctx->nb_streams; i++)
    {
        AVStream *in_stream = ifmt_ctx->streams[i];// 音频流、视频流、字幕流
        //如果是音频流,则打印音频的信息
        if (AVMEDIA_TYPE_AUDIO == in_stream->codecpar->codec_type)
        {
            printf("----- Audio info:\n");
            // index: 每个流成分在ffmpeg解复用分析后都有唯一的index作为标识
            printf("index:%d\n", in_stream->index);
            // sample_rate: 音频编解码器的采样率,单位为Hz
            printf("samplerate:%dHz\n", in_stream->codecpar->sample_rate);
            // codecpar->format: 音频采样格式
            if (AV_SAMPLE_FMT_FLTP == in_stream->codecpar->format)
            {
                printf("sampleformat:AV_SAMPLE_FMT_FLTP\n");
            }
            else if (AV_SAMPLE_FMT_S16P == in_stream->codecpar->format)
            {
                printf("sampleformat:AV_SAMPLE_FMT_S16P\n");
            }
            // channels: 音频信道数目
            printf("channel number:%d\n", in_stream->codecpar->channels);
            // codec_id: 音频压缩编码格式
            if (AV_CODEC_ID_AAC == in_stream->codecpar->codec_id)
            {
                printf("audio codec:AAC\n");
            }
            else if (AV_CODEC_ID_MP3 == in_stream->codecpar->codec_id)
            {
                printf("audio codec:MP3\n");
            }
            else
            {
                printf("audio codec_id:%d\n", in_stream->codecpar->codec_id);
            }
            // 音频总时长,单位为秒。注意如果把单位放大为毫秒或者微妙,音频总时长跟视频总时长不一定相等的
            if(in_stream->duration != AV_NOPTS_VALUE)
            {
                int duration_audio = (in_stream->duration) * av_q2d(in_stream->time_base);
                //将音频总时长转换为时分秒的格式打印到控制台上
                printf("audio duration: %02d:%02d:%02d\n",
                       duration_audio / 3600, (duration_audio % 3600) / 60, (duration_audio % 60));
            }
            else
            {
                printf("audio duration unknown");
            }

            printf("\n");

            audioindex = i; // 获取音频的索引
        }
        else if (AVMEDIA_TYPE_VIDEO == in_stream->codecpar->codec_type)  //如果是视频流,则打印视频的信息
        {
            printf("----- Video info:\n");
            printf("index:%d\n", in_stream->index);
            // avg_frame_rate: 视频帧率,单位为fps,表示每秒出现多少帧
            printf("fps:%lffps\n", av_q2d(in_stream->avg_frame_rate));
            if (AV_CODEC_ID_MPEG4 == in_stream->codecpar->codec_id) //视频压缩编码格式
            {
                printf("video codec:MPEG4\n");
            }
            else if (AV_CODEC_ID_H264 == in_stream->codecpar->codec_id) //视频压缩编码格式
            {
                printf("video codec:H264\n");
            }
            else
            {
                printf("video codec_id:%d\n", in_stream->codecpar->codec_id);
            }
            // 视频帧宽度和帧高度
            printf("width:%d height:%d\n", in_stream->codecpar->width,
                   in_stream->codecpar->height);
            //视频总时长,单位为秒。注意如果把单位放大为毫秒或者微妙,音频总时长跟视频总时长不一定相等的
            if(in_stream->duration != AV_NOPTS_VALUE)
            {
                int duration_video = (in_stream->duration) * av_q2d(in_stream->time_base);
                printf("video duration: %02d:%02d:%02d\n",
                       duration_video / 3600,
                       (duration_video % 3600) / 60,
                       (duration_video % 60)); //将视频总时长转换为时分秒的格式打印到控制台上
            }
            else
            {
                printf("video duration unknown");
            }

            printf("\n");
            videoindex = i;
        }
    }

    AVPacket *pkt = av_packet_alloc();

    int pkt_count = 0;
    int print_max_count = 10;
    printf("\n-----av_read_frame start\n");
    while (1)
    {
        ret = av_read_frame(ifmt_ctx, pkt);
        if (ret < 0)
        {
            printf("av_read_frame end\n");
            break;
        }

        if(pkt_count++ < print_max_count)
        {
            if (pkt->stream_index == audioindex)
            {
                printf("audio pts: %lld\n", pkt->pts);
                printf("audio dts: %lld\n", pkt->dts);
                printf("audio size: %d\n", pkt->size);
                printf("audio pos: %lld\n", pkt->pos);
                printf("audio duration: %lf\n\n",
                       pkt->duration * av_q2d(ifmt_ctx->streams[audioindex]->time_base));
            }
            else if (pkt->stream_index == videoindex)
            {
                printf("video pts: %lld\n", pkt->pts);
                printf("video dts: %lld\n", pkt->dts);
                printf("video size: %d\n", pkt->size);
                printf("video pos: %lld\n", pkt->pos);
                printf("video duration: %lf\n\n",
                       pkt->duration * av_q2d(ifmt_ctx->streams[videoindex]->time_base));
            }
            else
            {
                printf("unknown stream_index:\n", pkt->stream_index);
            }
        }

        av_packet_unref(pkt);
    }

    if(pkt)
        av_packet_free(&pkt);
failed:
    if(ifmt_ctx)
        avformat_close_input(&ifmt_ctx);


    getchar(); //加上这一句,防止程序打印完信息马上退出
    return 0;
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185
  • 186
  • 187
  • 188
  • 189
  • 190
  • 191
  • 192
  • 193
  • 194
  • 195
  • 196
  • 197
  • 198
  • 199
  • 200
  • 201
  • 202
  • 203
  • 204
  • 205
  • 206
  • 207
  • 208
  • 209
  • 210
  • 211
  • 212
  • 213
  • 214
  • 215
  • 216
  • 217
  • 218
  • 219

二、读取媒体文件,将aac帧提取出到本地。

#include <stdio.h>
#include <libavutil/log.h>
#include <libavformat/avio.h>
#include <libavformat/avformat.h>

#define ADTS_HEADER_LEN 7;

const int sampling_frequencies[] = {
96000, // 0x0
88200, // 0x1
64000, // 0x2
48000, // 0x3
44100, // 0x4
32000, // 0x5
24000, // 0x6
22050, // 0x7
16000, // 0x8
12000, // 0x9
11025, // 0xa
8000 // 0xb
// 0xc d e f是保留的
};

int adts_header(char * const p_adts_header, const int data_length,
const int profile, const int samplerate,
const int channels)
{

<span class="token keyword">int</span> sampling_frequency_index <span class="token operator">=</span> <span class="token number">3</span><span class="token punctuation">;</span> <span class="token comment">// 默认使用48000hz</span>
<span class="token keyword">int</span> adtsLen <span class="token operator">=</span> data_length <span class="token operator">+</span> <span class="token number">7</span><span class="token punctuation">;</span>

<span class="token keyword">int</span> frequencies_size <span class="token operator">=</span> <span class="token keyword">sizeof</span><span class="token punctuation">(</span>sampling_frequencies<span class="token punctuation">)</span> <span class="token operator">/</span> <span class="token keyword">sizeof</span><span class="token punctuation">(</span>sampling_frequencies<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">int</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
<span class="token keyword">for</span><span class="token punctuation">(</span>i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> frequencies_size<span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token keyword">if</span><span class="token punctuation">(</span>sampling_frequencies<span class="token punctuation">[</span>i<span class="token punctuation">]</span> <span class="token operator">==</span> samplerate<span class="token punctuation">)</span>
    <span class="token punctuation">{<!-- --></span>
        sampling_frequency_index <span class="token operator">=</span> i<span class="token punctuation">;</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token keyword">if</span><span class="token punctuation">(</span>i <span class="token operator">&gt;=</span> frequencies_size<span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"unsupport samplerate:%d\n"</span><span class="token punctuation">,</span> samplerate<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

p_adts_header<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token number">0xff</span><span class="token punctuation">;</span>         <span class="token comment">//syncword:0xfff                          高8bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token number">0xf0</span><span class="token punctuation">;</span>         <span class="token comment">//syncword:0xfff                          低4bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">3</span><span class="token punctuation">)</span><span class="token punctuation">;</span>    <span class="token comment">//MPEG Version:0 for MPEG-4,1 for MPEG-2  1bit</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">1</span><span class="token punctuation">)</span><span class="token punctuation">;</span>    <span class="token comment">//Layer:0                                 2bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token number">1</span><span class="token punctuation">;</span>           <span class="token comment">//protection absent:1                     1bit</span>

p_adts_header<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token punctuation">(</span>profile<span class="token punctuation">)</span><span class="token operator">&lt;&lt;</span><span class="token number">6</span><span class="token punctuation">;</span>            <span class="token comment">//profile:profile               2bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span>sampling_frequency_index <span class="token operator">&amp;</span> <span class="token number">0x0f</span><span class="token punctuation">)</span><span class="token operator">&lt;&lt;</span><span class="token number">2</span><span class="token punctuation">;</span> <span class="token comment">//sampling frequency index:sampling_frequency_index  4bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">1</span><span class="token punctuation">)</span><span class="token punctuation">;</span>             <span class="token comment">//private bit:0                   1bit</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span>channels <span class="token operator">&amp;</span> <span class="token number">0x04</span><span class="token punctuation">)</span><span class="token operator">&gt;&gt;</span><span class="token number">2</span><span class="token punctuation">;</span> <span class="token comment">//channel configuration:channels  高1bit</span>

p_adts_header<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token punctuation">(</span>channels <span class="token operator">&amp;</span> <span class="token number">0x03</span><span class="token punctuation">)</span><span class="token operator">&lt;&lt;</span><span class="token number">6</span><span class="token punctuation">;</span> <span class="token comment">//channel configuration:channels 低2bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">5</span><span class="token punctuation">)</span><span class="token punctuation">;</span>               <span class="token comment">//original:0                1bit</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">4</span><span class="token punctuation">)</span><span class="token punctuation">;</span>               <span class="token comment">//home:0                    1bit</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">3</span><span class="token punctuation">)</span><span class="token punctuation">;</span>               <span class="token comment">//copyright id bit:0        1bit</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">&lt;&lt;</span> <span class="token number">2</span><span class="token punctuation">)</span><span class="token punctuation">;</span>               <span class="token comment">//copyright id start:0      1bit</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token punctuation">(</span><span class="token punctuation">(</span>adtsLen <span class="token operator">&amp;</span> <span class="token number">0x1800</span><span class="token punctuation">)</span> <span class="token operator">&gt;&gt;</span> <span class="token number">11</span><span class="token punctuation">)</span><span class="token punctuation">;</span>           <span class="token comment">//frame length:value   高2bits</span>

p_adts_header<span class="token punctuation">[</span><span class="token number">4</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token keyword">uint8_t</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">(</span>adtsLen <span class="token operator">&amp;</span> <span class="token number">0x7f8</span><span class="token punctuation">)</span> <span class="token operator">&gt;&gt;</span> <span class="token number">3</span><span class="token punctuation">)</span><span class="token punctuation">;</span>     <span class="token comment">//frame length:value    中间8bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">5</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token keyword">uint8_t</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">(</span>adtsLen <span class="token operator">&amp;</span> <span class="token number">0x7</span><span class="token punctuation">)</span> <span class="token operator">&lt;&lt;</span> <span class="token number">5</span><span class="token punctuation">)</span><span class="token punctuation">;</span>       <span class="token comment">//frame length:value    低3bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">5</span><span class="token punctuation">]</span> <span class="token operator">|=</span> <span class="token number">0x1f</span><span class="token punctuation">;</span>                                 <span class="token comment">//buffer fullness:0x7ff 高5bits</span>
p_adts_header<span class="token punctuation">[</span><span class="token number">6</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token number">0xfc</span><span class="token punctuation">;</span>      <span class="token comment">//‭11111100‬       //buffer fullness:0x7ff 低6bits</span>
<span class="token comment">// number_of_raw_data_blocks_in_frame:</span>
<span class="token comment">//    表示ADTS帧中有number_of_raw_data_blocks_in_frame + 1个AAC原始帧。</span>

<span class="token keyword">return</span> <span class="token number">0</span><span class="token punctuation">;</span>

}

int main(int argc, char *argv[])
{
int ret = -1;
char errors[1024];

<span class="token keyword">char</span> <span class="token operator">*</span>in_filename <span class="token operator">=</span> <span class="token constant">NULL</span><span class="token punctuation">;</span>
<span class="token keyword">char</span> <span class="token operator">*</span>aac_filename <span class="token operator">=</span> <span class="token constant">NULL</span><span class="token punctuation">;</span>

FILE <span class="token operator">*</span>aac_fd <span class="token operator">=</span> <span class="token constant">NULL</span><span class="token punctuation">;</span>

<span class="token keyword">int</span> audio_index <span class="token operator">=</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token keyword">int</span> len <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>


AVFormatContext <span class="token operator">*</span>ifmt_ctx <span class="token operator">=</span> <span class="token constant">NULL</span><span class="token punctuation">;</span>
AVPacket pkt<span class="token punctuation">;</span>

<span class="token comment">// 设置打印级别</span>
<span class="token function">av_log_set_level</span><span class="token punctuation">(</span>AV_LOG_DEBUG<span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">if</span><span class="token punctuation">(</span>argc <span class="token operator">&lt;</span> <span class="token number">3</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"the count of parameters should be more than three!\n"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

in_filename <span class="token operator">=</span> argv<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">;</span>      <span class="token comment">// 输入文件</span>
aac_filename <span class="token operator">=</span> argv<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">;</span>     <span class="token comment">// 输出文件</span>

<span class="token keyword">if</span><span class="token punctuation">(</span>in_filename <span class="token operator">==</span> <span class="token constant">NULL</span> <span class="token operator">||</span> aac_filename <span class="token operator">==</span> <span class="token constant">NULL</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"src or dts file is null, plz check them!\n"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

aac_fd <span class="token operator">=</span> <span class="token function">fopen</span><span class="token punctuation">(</span>aac_filename<span class="token punctuation">,</span> <span class="token string">"wb"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token operator">!</span>aac_fd<span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"Could not open destination file %s\n"</span><span class="token punctuation">,</span> aac_filename<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 打开输入文件</span>
<span class="token keyword">if</span><span class="token punctuation">(</span><span class="token punctuation">(</span>ret <span class="token operator">=</span> <span class="token function">avformat_open_input</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>ifmt_ctx<span class="token punctuation">,</span> in_filename<span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">)</span><span class="token punctuation">)</span> <span class="token operator">&lt;</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">av_strerror</span><span class="token punctuation">(</span>ret<span class="token punctuation">,</span> errors<span class="token punctuation">,</span> <span class="token number">1024</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"Could not open source file: %s, %d(%s)\n"</span><span class="token punctuation">,</span>
           in_filename<span class="token punctuation">,</span>
           ret<span class="token punctuation">,</span>
           errors<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 获取解码器信息</span>
<span class="token keyword">if</span><span class="token punctuation">(</span><span class="token punctuation">(</span>ret <span class="token operator">=</span> <span class="token function">avformat_find_stream_info</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">)</span><span class="token punctuation">)</span> <span class="token operator">&lt;</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">av_strerror</span><span class="token punctuation">(</span>ret<span class="token punctuation">,</span> errors<span class="token punctuation">,</span> <span class="token number">1024</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"failed to find stream information: %s, %d(%s)\n"</span><span class="token punctuation">,</span>
           in_filename<span class="token punctuation">,</span>
           ret<span class="token punctuation">,</span>
           errors<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// dump媒体信息</span>
<span class="token function">av_dump_format</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">,</span> in_filename<span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 初始化packet</span>
<span class="token function">av_init_packet</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>pkt<span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 查找audio对应的steam index</span>
audio_index <span class="token operator">=</span> <span class="token function">av_find_best_stream</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> AVMEDIA_TYPE_AUDIO<span class="token punctuation">,</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">,</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">if</span><span class="token punctuation">(</span>audio_index <span class="token operator">&lt;</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"Could not find %s stream in input file %s\n"</span><span class="token punctuation">,</span>
           <span class="token function">av_get_media_type_string</span><span class="token punctuation">(</span>AVMEDIA_TYPE_AUDIO<span class="token punctuation">)</span><span class="token punctuation">,</span>
           in_filename<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token function">AVERROR</span><span class="token punctuation">(</span>EINVAL<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 打印AAC级别</span>
<span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"audio profile:%d, FF_PROFILE_AAC_LOW:%d\n"</span><span class="token punctuation">,</span>
       ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>audio_index<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token operator">-&gt;</span>profile<span class="token punctuation">,</span>
       FF_PROFILE_AAC_LOW<span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">if</span><span class="token punctuation">(</span>ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>audio_index<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token operator">-&gt;</span>codec_id <span class="token operator">!=</span> AV_CODEC_ID_AAC<span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"the media file no contain AAC stream, it's codec_id is %d\n"</span><span class="token punctuation">,</span>
           ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>audio_index<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token operator">-&gt;</span>codec_id<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">goto</span> failed<span class="token punctuation">;</span>
<span class="token punctuation">}</span>
<span class="token comment">// 读取媒体文件,并把aac数据帧写入到本地文件</span>
<span class="token keyword">while</span><span class="token punctuation">(</span><span class="token function">av_read_frame</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> <span class="token operator">&amp;</span>pkt<span class="token punctuation">)</span> <span class="token operator">&gt;=</span><span class="token number">0</span> <span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token keyword">if</span><span class="token punctuation">(</span>pkt<span class="token punctuation">.</span>stream_index <span class="token operator">==</span> audio_index<span class="token punctuation">)</span>
    <span class="token punctuation">{<!-- --></span>
        <span class="token keyword">char</span> adts_header_buf<span class="token punctuation">[</span><span class="token number">7</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token punctuation">{<!-- --></span><span class="token number">0</span><span class="token punctuation">}</span><span class="token punctuation">;</span>
        <span class="token function">adts_header</span><span class="token punctuation">(</span>adts_header_buf<span class="token punctuation">,</span> pkt<span class="token punctuation">.</span>size<span class="token punctuation">,</span>
                    ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>audio_index<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token operator">-&gt;</span>profile<span class="token punctuation">,</span>
                    ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>audio_index<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token operator">-&gt;</span>sample_rate<span class="token punctuation">,</span>
                    ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>audio_index<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token operator">-&gt;</span>channels<span class="token punctuation">)</span><span class="token punctuation">;</span>
        <span class="token function">fwrite</span><span class="token punctuation">(</span>adts_header_buf<span class="token punctuation">,</span> <span class="token number">1</span><span class="token punctuation">,</span> <span class="token number">7</span><span class="token punctuation">,</span> aac_fd<span class="token punctuation">)</span><span class="token punctuation">;</span>  <span class="token comment">// 写adts header , ts流不适用,ts流分离出来的packet带了adts header</span>
        len <span class="token operator">=</span> <span class="token function">fwrite</span><span class="token punctuation">(</span> pkt<span class="token punctuation">.</span>data<span class="token punctuation">,</span> <span class="token number">1</span><span class="token punctuation">,</span> pkt<span class="token punctuation">.</span>size<span class="token punctuation">,</span> aac_fd<span class="token punctuation">)</span><span class="token punctuation">;</span>   <span class="token comment">// 写adts data</span>
        <span class="token keyword">if</span><span class="token punctuation">(</span>len <span class="token operator">!=</span> pkt<span class="token punctuation">.</span>size<span class="token punctuation">)</span>
        <span class="token punctuation">{<!-- --></span>
            <span class="token function">av_log</span><span class="token punctuation">(</span><span class="token constant">NULL</span><span class="token punctuation">,</span> AV_LOG_DEBUG<span class="token punctuation">,</span> <span class="token string">"warning, length of writed data isn't equal pkt.size(%d, %d)\n"</span><span class="token punctuation">,</span>
                   len<span class="token punctuation">,</span>
                   pkt<span class="token punctuation">.</span>size<span class="token punctuation">)</span><span class="token punctuation">;</span>
        <span class="token punctuation">}</span>
    <span class="token punctuation">}</span>
    <span class="token function">av_packet_unref</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>pkt<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

failed:
// 关闭输入文件
if(ifmt_ctx)
{
avformat_close_input(&ifmt_ctx);
}
if(aac_fd)
{
fclose(aac_fd);
}

<span class="token keyword">return</span> <span class="token number">0</span><span class="token punctuation">;</span>

}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185
  • 186
  • 187
  • 188
  • 189
  • 190
  • 191
  • 192
  • 193
  • 194
  • 195
  • 196
  • 197
  • 198
  • 199
  • 200
  • 201
  • 202

三、从媒体文件中提取出h264视频帧到本地

#include <stdio.h>
#include <libavutil/log.h>
#include <libavformat/avio.h>
#include <libavformat/avformat.h>

static char err_buf[128] = {0};
static char* av_get_err(int errnum)
{
av_strerror(errnum, err_buf, 128);
return err_buf;
}

/*
AvCodecContext->extradata[]中为nalu长度

  • codec_extradata:
  • 1, 64, 0, 1f, ff, e1, [0, 18], 67, 64, 0, 1f, ac, c8, 60, 78, 1b, 7e,
  • 78, 40, 0, 0, fa, 40, 0, 3a, 98, 3, c6, c, 66, 80,
  • 1, [0, 5],68, e9, 78, bc, b0, 0,
    */

//ffmpeg -i 2018.mp4 -codec copy -bsf:h264_mp4toannexb -f h264 tmp.h264
//ffmpeg 从mp4上提取H264的nalu h
int main(int argc, char argv)
{
AVFormatContext ifmt_ctx = NULL;
int videoindex = -1;
AVPacket pkt = NULL;
int ret = -1;
int file_end = 0; // 文件是否读取结束

<span class="token keyword">if</span><span class="token punctuation">(</span>argc <span class="token operator">&lt;</span> <span class="token number">3</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"usage inputfile outfile\n"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>
FILE <span class="token operator">*</span>outfp<span class="token operator">=</span><span class="token function">fopen</span><span class="token punctuation">(</span>argv<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">,</span><span class="token string">"wb"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"in:%s out:%s\n"</span><span class="token punctuation">,</span> argv<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">,</span> argv<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 分配解复用器的内存,使用avformat_close_input释放</span>
ifmt_ctx <span class="token operator">=</span> <span class="token function">avformat_alloc_context</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token operator">!</span>ifmt_ctx<span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"[error] Could not allocate context.\n"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 根据url打开码流,并选择匹配的解复用器</span>
ret <span class="token operator">=</span> <span class="token function">avformat_open_input</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>ifmt_ctx<span class="token punctuation">,</span>argv<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">if</span><span class="token punctuation">(</span>ret <span class="token operator">!=</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"[error]avformat_open_input: %s\n"</span><span class="token punctuation">,</span> <span class="token function">av_get_err</span><span class="token punctuation">(</span>ret<span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 读取媒体文件的部分数据包以获取码流信息</span>
ret <span class="token operator">=</span> <span class="token function">avformat_find_stream_info</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">if</span><span class="token punctuation">(</span>ret <span class="token operator">&lt;</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"[error]avformat_find_stream_info: %s\n"</span><span class="token punctuation">,</span> <span class="token function">av_get_err</span><span class="token punctuation">(</span>ret<span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token function">avformat_close_input</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>ifmt_ctx<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 查找出哪个码流是video/audio/subtitles</span>
videoindex <span class="token operator">=</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token comment">// 推荐的方式</span>
videoindex <span class="token operator">=</span> <span class="token function">av_find_best_stream</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> AVMEDIA_TYPE_VIDEO<span class="token punctuation">,</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">,</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">,</span> <span class="token constant">NULL</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">if</span><span class="token punctuation">(</span>videoindex <span class="token operator">==</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"Didn't find a video stream.\n"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token function">avformat_close_input</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>ifmt_ctx<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token comment">// 分配数据包</span>
pkt <span class="token operator">=</span> <span class="token function">av_packet_alloc</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token function">av_init_packet</span><span class="token punctuation">(</span>pkt<span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token comment">// 1 获取相应的比特流过滤器</span>
<span class="token comment">//FLV/MP4/MKV等结构中,h264需要h264_mp4toannexb处理。添加SPS/PPS等信息。</span>
<span class="token comment">// FLV封装时,可以把多个NALU放在一个VIDEO TAG中,结构为4B NALU长度+NALU1+4B NALU长度+NALU2+...,</span>
<span class="token comment">// 需要做的处理把4B长度换成00000001或者000001</span>
<span class="token keyword">const</span> AVBitStreamFilter <span class="token operator">*</span>bsfilter <span class="token operator">=</span> <span class="token function">av_bsf_get_by_name</span><span class="token punctuation">(</span><span class="token string">"h264_mp4toannexb"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
AVBSFContext <span class="token operator">*</span>bsf_ctx <span class="token operator">=</span> <span class="token constant">NULL</span><span class="token punctuation">;</span>
<span class="token comment">// 2 初始化过滤器上下文</span>
<span class="token function">av_bsf_alloc</span><span class="token punctuation">(</span>bsfilter<span class="token punctuation">,</span> <span class="token operator">&amp;</span>bsf_ctx<span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">//AVBSFContext;</span>
<span class="token comment">// 3 添加解码器属性</span>
<span class="token function">avcodec_parameters_copy</span><span class="token punctuation">(</span>bsf_ctx<span class="token operator">-&gt;</span>par_in<span class="token punctuation">,</span> ifmt_ctx<span class="token operator">-&gt;</span>streams<span class="token punctuation">[</span>videoindex<span class="token punctuation">]</span><span class="token operator">-&gt;</span>codecpar<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token function">av_bsf_init</span><span class="token punctuation">(</span>bsf_ctx<span class="token punctuation">)</span><span class="token punctuation">;</span>

file_end <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
<span class="token keyword">while</span> <span class="token punctuation">(</span><span class="token number">0</span> <span class="token operator">==</span> file_end<span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token punctuation">(</span>ret <span class="token operator">=</span> <span class="token function">av_read_frame</span><span class="token punctuation">(</span>ifmt_ctx<span class="token punctuation">,</span> pkt<span class="token punctuation">)</span><span class="token punctuation">)</span> <span class="token operator">&lt;</span> <span class="token number">0</span><span class="token punctuation">)</span>
    <span class="token punctuation">{<!-- --></span>
        <span class="token comment">// 没有更多包可读</span>
        file_end <span class="token operator">=</span> <span class="token number">1</span><span class="token punctuation">;</span>
        <span class="token function">printf</span><span class="token punctuation">(</span><span class="token string">"read file end: ret:%d\n"</span><span class="token punctuation">,</span> ret<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span>
    <span class="token keyword">if</span><span class="token punctuation">(</span>ret <span class="token operator">==</span> <span class="token number">0</span> <span class="token operator">&amp;&amp;</span> pkt<span class="token operator">-&gt;</span>stream_index <span class="token operator">==</span> videoindex<span class="token punctuation">)</span>
    <span class="token punctuation">{<!-- --></span>

#if 0
int input_size = pkt->size;
int out_pkt_count = 0;
if (av_bsf_send_packet(bsf_ctx, pkt) != 0) // bitstreamfilter内部去维护内存空间
{
av_packet_unref(pkt); // 你不用了就把资源释放掉
continue; // 继续送
}
av_packet_unref(pkt); // 释放资源
while(av_bsf_receive_packet(bsf_ctx, pkt) 0)
{
out_pkt_count++;
// printf(“fwrite size:%d\n”, pkt->size);
size_t size = fwrite(pkt->data, 1, pkt->size, outfp);
if(size != pkt->size)
{
printf(“fwrite failed-> write:%u, pkt_size:%u\n”, size, pkt->size);
}
av_packet_unref(pkt);
}
if(out_pkt_count >= 2)
{
printf(“cur pkt(size:%d) only get 1 out pkt, it get %d pkts\n”,
input_size, out_pkt_count);
}
#else // TS流可以直接写入
size_t size = fwrite(pkt->data, 1, pkt->size, outfp);
if(size != pkt->size)
{
printf(“fwrite failed-> write:%u, pkt_size:%u\n”, size, pkt->size);
}
av_packet_unref(pkt);
#endif
}
else
{
if(ret 0)
av_packet_unref(pkt); // 释放内存
}
}
if(outfp)
fclose(outfp);
if(bsf_ctx)
av_bsf_free(&bsf_ctx);
if(pkt)
av_packet_free(&pkt);
if(ifmt_ctx)
avformat_close_input(&ifmt_ctx);
printf(“finish\n”);

<span class="token keyword">return</span> <span class="token number">0</span><span class="token punctuation">;</span>

}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156

四、flv解封装

(1)FlvMetaData.cpp

#include "FlvMetaData.h"

FlvMetaData::FlvMetaData(uint8_t *meta, unsigned int length) {

m_meta <span class="token operator">=</span> meta<span class="token punctuation">;</span>
m_length <span class="token operator">=</span> length<span class="token punctuation">;</span>

m_duration <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_width <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_height <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_framerate <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_videodatarate <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_audiodatarate <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_videocodecid <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_audiosamplerate <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_audiosamplesize <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
m_stereo <span class="token operator">=</span> <span class="token boolean">false</span><span class="token punctuation">;</span>

<span class="token function">parseMeta</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

}

FlvMetaData::FlvMetaData(const FlvMetaData& r) {

m_length <span class="token operator">=</span> r<span class="token punctuation">.</span>m_length<span class="token punctuation">;</span>
m_meta <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token keyword">uint8_t</span><span class="token punctuation">[</span>m_length<span class="token punctuation">]</span><span class="token punctuation">;</span>
<span class="token function">memcpy</span><span class="token punctuation">(</span>m_meta<span class="token punctuation">,</span> r<span class="token punctuation">.</span>m_meta<span class="token punctuation">,</span> m_length<span class="token punctuation">)</span><span class="token punctuation">;</span>

m_duration <span class="token operator">=</span> r<span class="token punctuation">.</span>m_duration<span class="token punctuation">;</span>
m_width <span class="token operator">=</span> r<span class="token punctuation">.</span>m_width<span class="token punctuation">;</span>
m_height <span class="token operator">=</span> r<span class="token punctuation">.</span>m_height<span class="token punctuation">;</span>
m_framerate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_framerate<span class="token punctuation">;</span>
m_videodatarate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_videodatarate<span class="token punctuation">;</span>
m_audiodatarate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_audiodatarate<span class="token punctuation">;</span>
m_videocodecid <span class="token operator">=</span> r<span class="token punctuation">.</span>m_videocodecid<span class="token punctuation">;</span>
m_audiosamplerate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_audiosamplerate<span class="token punctuation">;</span>
m_audiosamplesize <span class="token operator">=</span> r<span class="token punctuation">.</span>m_audiosamplesize<span class="token punctuation">;</span>
m_stereo <span class="token operator">=</span> r<span class="token punctuation">.</span>m_stereo<span class="token punctuation">;</span>

}

FlvMetaData& FlvMetaData::operator=(const FlvMetaData& r) {

<span class="token keyword">if</span><span class="token punctuation">(</span><span class="token keyword">this</span> <span class="token operator">==</span> <span class="token operator">&amp;</span>r<span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
    <span class="token keyword">return</span> <span class="token operator">*</span><span class="token keyword">this</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token keyword">if</span><span class="token punctuation">(</span>m_meta <span class="token operator">!=</span> <span class="token constant">NULL</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
    <span class="token keyword">delete</span> m_meta<span class="token punctuation">;</span>
<span class="token punctuation">}</span>

m_length <span class="token operator">=</span> r<span class="token punctuation">.</span>m_length<span class="token punctuation">;</span>
m_meta <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token keyword">uint8_t</span><span class="token punctuation">[</span>m_length<span class="token punctuation">]</span><span class="token punctuation">;</span>
<span class="token function">memcpy</span><span class="token punctuation">(</span>m_meta<span class="token punctuation">,</span> r<span class="token punctuation">.</span>m_meta<span class="token punctuation">,</span> m_length<span class="token punctuation">)</span><span class="token punctuation">;</span>

m_duration <span class="token operator">=</span> r<span class="token punctuation">.</span>m_duration<span class="token punctuation">;</span>
m_width <span class="token operator">=</span> r<span class="token punctuation">.</span>m_width<span class="token punctuation">;</span>
m_height <span class="token operator">=</span> r<span class="token punctuation">.</span>m_height<span class="token punctuation">;</span>
m_framerate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_framerate<span class="token punctuation">;</span>
m_videodatarate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_videodatarate<span class="token punctuation">;</span>
m_audiodatarate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_audiodatarate<span class="token punctuation">;</span>
m_videocodecid <span class="token operator">=</span> r<span class="token punctuation">.</span>m_videocodecid<span class="token punctuation">;</span>
m_audiosamplerate <span class="token operator">=</span> r<span class="token punctuation">.</span>m_audiosamplerate<span class="token punctuation">;</span>
m_audiosamplesize <span class="token operator">=</span> r<span class="token punctuation">.</span>m_audiosamplesize<span class="token punctuation">;</span>
m_stereo <span class="token operator">=</span> r<span class="token punctuation">.</span>m_stereo<span class="token punctuation">;</span>

<span class="token keyword">return</span> <span class="token operator">*</span><span class="token keyword">this</span><span class="token punctuation">;</span>

}

FlvMetaData::~FlvMetaData() {

<span class="token keyword">if</span><span class="token punctuation">(</span>m_meta <span class="token operator">!=</span> <span class="token constant">NULL</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
    <span class="token keyword">delete</span> m_meta<span class="token punctuation">;</span>
    m_meta <span class="token operator">=</span> <span class="token constant">NULL</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

}

void FlvMetaData::parseMeta() {

<span class="token keyword">unsigned</span> <span class="token keyword">int</span> arrayLen <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
<span class="token keyword">unsigned</span> <span class="token keyword">int</span> offset <span class="token operator">=</span> TAG_HEAD_LEN <span class="token operator">+</span> <span class="token number">13</span><span class="token punctuation">;</span>

<span class="token keyword">unsigned</span> <span class="token keyword">int</span> nameLen <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> numValue <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
<span class="token keyword">bool</span> boolValue <span class="token operator">=</span> <span class="token boolean">false</span><span class="token punctuation">;</span>

<span class="token keyword">if</span><span class="token punctuation">(</span>m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x08</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>

    arrayLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
    arrayLen <span class="token operator">=</span> arrayLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
    arrayLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
    arrayLen <span class="token operator">=</span> arrayLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
    arrayLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
    arrayLen <span class="token operator">=</span> arrayLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
    arrayLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>

    <span class="token comment">//cerr &lt;&lt; "ArrayLen = " &lt;&lt; arrayLen &lt;&lt; endl;</span>
<span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token punctuation">{<!-- --></span>
    <span class="token comment">//TODO:</span>
    cerr <span class="token operator">&lt;&lt;</span> <span class="token string">"metadata format error!!!"</span> <span class="token operator">&lt;&lt;</span> endl<span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token keyword">for</span><span class="token punctuation">(</span><span class="token keyword">unsigned</span> <span class="token keyword">int</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> arrayLen<span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>

    numValue <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
    boolValue <span class="token operator">=</span> <span class="token boolean">false</span><span class="token punctuation">;</span>

    nameLen <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
    nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
    nameLen <span class="token operator">=</span> nameLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
    nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
    <span class="token comment">//cerr &lt;&lt; "name length=" &lt;&lt; nameLen &lt;&lt; " ";</span>

    <span class="token keyword">char</span> name<span class="token punctuation">[</span>nameLen <span class="token operator">+</span> <span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">;</span>

#if DEBUG
printf(“\norign \n”);
for(unsigned int i = 0; i < nameLen + 3; i++) {
printf(“%x “, m_meta[offset + i]);
}
printf(”\n”);
#endif

    <span class="token function">memset</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">,</span> <span class="token keyword">sizeof</span><span class="token punctuation">(</span>name<span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token function">memcpy</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token operator">&amp;</span>m_meta<span class="token punctuation">[</span>offset<span class="token punctuation">]</span><span class="token punctuation">,</span> nameLen<span class="token punctuation">)</span><span class="token punctuation">;</span>
    name<span class="token punctuation">[</span>nameLen <span class="token operator">+</span> <span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token char">'\0'</span><span class="token punctuation">;</span>
    offset <span class="token operator">+=</span> nameLen<span class="token punctuation">;</span>
    <span class="token comment">//cerr &lt;&lt; "name=" &lt;&lt; name &lt;&lt; " ";</span>

#if DEBUG
printf(“memcpy\n”);
for(unsigned int i = 0; i < nameLen; i++) {
printf(“%x “, name[i]);
}
printf(”\n”);
#endif
switch(m_meta[offset++]) {
case 0x0: //Number type

        numValue <span class="token operator">=</span> <span class="token function">hexStr2double</span><span class="token punctuation">(</span><span class="token operator">&amp;</span>m_meta<span class="token punctuation">[</span>offset<span class="token punctuation">]</span><span class="token punctuation">,</span> <span class="token number">8</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
        offset <span class="token operator">+=</span> <span class="token number">8</span><span class="token punctuation">;</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>

    <span class="token keyword">case</span> <span class="token number">0x1</span><span class="token operator">:</span> <span class="token comment">//Boolean type</span>
        <span class="token keyword">if</span><span class="token punctuation">(</span>offset<span class="token operator">++</span> <span class="token operator">!=</span> <span class="token number">0x00</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
            boolValue <span class="token operator">=</span> <span class="token boolean">true</span><span class="token punctuation">;</span>
        <span class="token punctuation">}</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>

    <span class="token keyword">case</span> <span class="token number">0x2</span><span class="token operator">:</span> <span class="token comment">//String type</span>
        nameLen <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">=</span> nameLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
        offset <span class="token operator">+=</span> nameLen<span class="token punctuation">;</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>

    <span class="token keyword">case</span> <span class="token number">0x12</span><span class="token operator">:</span> <span class="token comment">//Long string type</span>
        nameLen <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">=</span> nameLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">=</span> nameLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">=</span> nameLen <span class="token operator">&lt;&lt;</span> <span class="token number">8</span><span class="token punctuation">;</span>
        nameLen <span class="token operator">|=</span> m_meta<span class="token punctuation">[</span>offset<span class="token operator">++</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
        offset <span class="token operator">+=</span> nameLen<span class="token punctuation">;</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>

    <span class="token comment">//FIXME:</span>
    <span class="token keyword">default</span><span class="token operator">:</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span>

    <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"duration"</span><span class="token punctuation">,</span> <span class="token number">8</span><span class="token punctuation">)</span>	<span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_duration <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"width"</span><span class="token punctuation">,</span> <span class="token number">5</span><span class="token punctuation">)</span>	<span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_width <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"height"</span><span class="token punctuation">,</span> <span class="token number">6</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_height <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"framerate"</span><span class="token punctuation">,</span> <span class="token number">9</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_framerate <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"videodatarate"</span><span class="token punctuation">,</span> <span class="token number">13</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_videodatarate <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"audiodatarate"</span><span class="token punctuation">,</span> <span class="token number">13</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_audiodatarate <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"videocodecid"</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_videocodecid <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"audiosamplerate"</span><span class="token punctuation">,</span> <span class="token number">15</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_audiosamplerate <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"audiosamplesize"</span><span class="token punctuation">,</span> <span class="token number">15</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_audiosamplesize <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"audiocodecid"</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_audiocodecid <span class="token operator">=</span> numValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token keyword">if</span><span class="token punctuation">(</span><span class="token function">strncmp</span><span class="token punctuation">(</span>name<span class="token punctuation">,</span> <span class="token string">"stereo"</span><span class="token punctuation">,</span> <span class="token number">6</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        m_stereo <span class="token operator">=</span> boolValue<span class="token punctuation">;</span>
    <span class="token punctuation">}</span>

<span class="token punctuation">}</span>

}

double FlvMetaData::hexStr2double(const uint8_t* hex, const unsigned int length) {

<span class="token keyword">double</span> ret <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
<span class="token keyword">char</span> hexstr<span class="token punctuation">[</span>length <span class="token operator">*</span> <span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
<span class="token function">memset</span><span class="token punctuation">(</span>hexstr<span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">,</span> <span class="token keyword">sizeof</span><span class="token punctuation">(</span>hexstr<span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">for</span><span class="token punctuation">(</span><span class="token keyword">unsigned</span> <span class="token keyword">int</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> length<span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
    <span class="token function">sprintf</span><span class="token punctuation">(</span>hexstr <span class="token operator">+</span> i <span class="token operator">*</span> <span class="token number">2</span><span class="token punctuation">,</span> <span class="token string">"%02x"</span><span class="token punctuation">,</span> hex<span class="token punctuation">[</span>i<span class="token punctuation">]</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token function">sscanf</span><span class="token punctuation">(</span>hexstr<span class="token punctuation">,</span> <span class="token string">"%llx"</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token keyword">unsigned</span> <span class="token keyword">long</span> <span class="token keyword">long</span><span class="token operator">*</span><span class="token punctuation">)</span><span class="token operator">&amp;</span>ret<span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">return</span> ret<span class="token punctuation">;</span>

}

double FlvMetaData::getDuration() {
return m_duration;
}

double FlvMetaData::getWidth() {
return m_width;
}

double FlvMetaData::getHeight() {
return m_height;
}

double FlvMetaData::getFramerate() {
return m_framerate;
}

double FlvMetaData::getVideoDatarate() {
return m_videodatarate;
}

double FlvMetaData::getAudioDatarate() {
return m_audiodatarate;
}

double FlvMetaData::getVideoCodecId() {
return m_videocodecid;
}

double FlvMetaData::getAudioSamplerate() {
return m_audiosamplerate;
}

double FlvMetaData::getAudioSamplesize() {
return m_audiosamplesize;
}

double FlvMetaData::getAudioCodecId() {
return m_audiocodecid;
}

bool FlvMetaData::getStereo() {
return m_stereo;
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185
  • 186
  • 187
  • 188
  • 189
  • 190
  • 191
  • 192
  • 193
  • 194
  • 195
  • 196
  • 197
  • 198
  • 199
  • 200
  • 201
  • 202
  • 203
  • 204
  • 205
  • 206
  • 207
  • 208
  • 209
  • 210
  • 211
  • 212
  • 213
  • 214
  • 215
  • 216
  • 217
  • 218
  • 219
  • 220
  • 221
  • 222
  • 223
  • 224
  • 225
  • 226
  • 227
  • 228
  • 229
  • 230
  • 231
  • 232
  • 233
  • 234
  • 235
  • 236
  • 237
  • 238
  • 239
  • 240
  • 241
  • 242
  • 243
  • 244
  • 245
  • 246
  • 247
  • 248
  • 249
  • 250
  • 251
  • 252
  • 253
  • 254
  • 255
  • 256
  • 257

(2) FlvMetaData.h

#ifndef FLVMETADATA_H
#define FLVMETADATA_H

#include <cstdint>

class FlvMetaData
{
public:
FlvMetaData(uint8_t *meta, uint32_t length);
~FlvMetaData();

<span class="token function">FlvMetaData</span><span class="token punctuation">(</span><span class="token keyword">const</span> FlvMetaData<span class="token operator">&amp;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
FlvMetaData<span class="token operator">&amp;</span> <span class="token keyword">operator</span><span class="token operator">=</span><span class="token punctuation">(</span><span class="token keyword">const</span> FlvMetaData<span class="token operator">&amp;</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">double</span> <span class="token function">getDuration</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getWidth</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getHeight</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getFramerate</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getVideoDatarate</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getAudioDatarate</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getVideoCodecId</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getAudioCodecId</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getAudioSamplerate</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">double</span> <span class="token function">getAudioSamplesize</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">bool</span> <span class="token function">getStereo</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

private:
//convert HEX to double
double hexStr2double(const uint8_t* hex, const uint32_t length);
void parseMeta();

private:
uint8_t *m_meta;
uint32_t m_length;

<span class="token keyword">double</span> m_duration<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_width<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_height<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_framerate<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_videodatarate<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_audiodatarate<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_videocodecid<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_audiocodecid<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_audiosamplerate<span class="token punctuation">;</span>
<span class="token keyword">double</span> m_audiosamplesize<span class="token punctuation">;</span>

<span class="token keyword">bool</span> m_stereo<span class="token punctuation">;</span>

};

#endif // FLVMETADATA_H

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51

(3)FlvPrase.cpp

#include <stdlib.h>
#include <string.h>
#include <assert.h>

#include <iostream>
#include <fstream>

#include “FlvParser.h”

using namespace std;

#define CheckBuffer(x) { if ((nBufSize-nOffset)<(x)) { nUsedLen = nOffset; return 0;} }

int CFlvParser::CAudioTag::_aacProfile;
int CFlvParser::CAudioTag::_sampleRateIndex;
int CFlvParser::CAudioTag::_channelConfig;

static const uint32_t nH264StartCode = 0x01000000;

CFlvParser::CFlvParser()
{
_pFlvHeader = NULL;
_vjj = new CVideojj();
}

CFlvParser::~CFlvParser()
{
for (int i = 0; i < _vpTag.size(); i++)
{
DestroyTag(_vpTag[i]);
delete _vpTag[i];
}
if (_vjj != NULL)
delete _vjj;
}

int CFlvParser::Parse(uint8_t *pBuf, int nBufSize, int &nUsedLen)
{
int nOffset = 0;

<span class="token keyword">if</span> <span class="token punctuation">(</span>_pFlvHeader <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">CheckBuffer</span><span class="token punctuation">(</span><span class="token number">9</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
    _pFlvHeader <span class="token operator">=</span> <span class="token function">CreateFlvHeader</span><span class="token punctuation">(</span>pBuf<span class="token operator">+</span>nOffset<span class="token punctuation">)</span><span class="token punctuation">;</span>
    nOffset <span class="token operator">+=</span> _pFlvHeader<span class="token operator">-&gt;</span>nHeadSize<span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token keyword">while</span> <span class="token punctuation">(</span><span class="token number">1</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token function">CheckBuffer</span><span class="token punctuation">(</span><span class="token number">15</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// nPrevSize(4字节) + Tag header(11字节)</span>
    <span class="token keyword">int</span> nPrevSize <span class="token operator">=</span> <span class="token function">ShowU32</span><span class="token punctuation">(</span>pBuf <span class="token operator">+</span> nOffset<span class="token punctuation">)</span><span class="token punctuation">;</span>
    nOffset <span class="token operator">+=</span> <span class="token number">4</span><span class="token punctuation">;</span>

    Tag <span class="token operator">*</span>pTag <span class="token operator">=</span> <span class="token function">CreateTag</span><span class="token punctuation">(</span>pBuf <span class="token operator">+</span> nOffset<span class="token punctuation">,</span> nBufSize<span class="token operator">-</span>nOffset<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">if</span> <span class="token punctuation">(</span>pTag <span class="token operator">==</span> <span class="token constant">NULL</span><span class="token punctuation">)</span>
    <span class="token punctuation">{<!-- --></span>
        nOffset <span class="token operator">-=</span> <span class="token number">4</span><span class="token punctuation">;</span>
        <span class="token keyword">break</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span>
    nOffset <span class="token operator">+=</span> <span class="token punctuation">(</span><span class="token number">11</span> <span class="token operator">+</span> pTag<span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize<span class="token punctuation">)</span><span class="token punctuation">;</span>

    _vpTag<span class="token punctuation">.</span><span class="token function">push_back</span><span class="token punctuation">(</span>pTag<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

nUsedLen <span class="token operator">=</span> nOffset<span class="token punctuation">;</span>
<span class="token keyword">return</span> <span class="token number">0</span><span class="token punctuation">;</span>

}

int CFlvParser::PrintInfo()
{
Stat();

cout <span class="token operator">&lt;&lt;</span> <span class="token string">"vnum: "</span> <span class="token operator">&lt;&lt;</span> _sStat<span class="token punctuation">.</span>nVideoNum <span class="token operator">&lt;&lt;</span> <span class="token string">" , anum: "</span> <span class="token operator">&lt;&lt;</span> _sStat<span class="token punctuation">.</span>nAudioNum <span class="token operator">&lt;&lt;</span> <span class="token string">" , mnum: "</span> <span class="token operator">&lt;&lt;</span> _sStat<span class="token punctuation">.</span>nMetaNum <span class="token operator">&lt;&lt;</span> endl<span class="token punctuation">;</span>
cout <span class="token operator">&lt;&lt;</span> <span class="token string">"maxTimeStamp: "</span> <span class="token operator">&lt;&lt;</span> _sStat<span class="token punctuation">.</span>nMaxTimeStamp <span class="token operator">&lt;&lt;</span> <span class="token string">" ,nLengthSize: "</span> <span class="token operator">&lt;&lt;</span> _sStat<span class="token punctuation">.</span>nLengthSize <span class="token operator">&lt;&lt;</span> endl<span class="token punctuation">;</span>
cout <span class="token operator">&lt;&lt;</span> <span class="token string">"Vjj SEI num: "</span> <span class="token operator">&lt;&lt;</span> _vjj<span class="token operator">-&gt;</span>_vVjjSEI<span class="token punctuation">.</span><span class="token function">size</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">&lt;&lt;</span> endl<span class="token punctuation">;</span>
<span class="token keyword">for</span> <span class="token punctuation">(</span><span class="token keyword">int</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> _vjj<span class="token operator">-&gt;</span>_vVjjSEI<span class="token punctuation">.</span><span class="token function">size</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span>
    cout <span class="token operator">&lt;&lt;</span> <span class="token string">"SEI time : "</span> <span class="token operator">&lt;&lt;</span> _vjj<span class="token operator">-&gt;</span>_vVjjSEI<span class="token punctuation">[</span>i<span class="token punctuation">]</span><span class="token punctuation">.</span>nTimeStamp <span class="token operator">&lt;&lt;</span> endl<span class="token punctuation">;</span>
<span class="token keyword">return</span> <span class="token number">1</span><span class="token punctuation">;</span>

}

int CFlvParser::DumpH264(const std::string &path)
{
fstream f;
f.open(path.c_str(), ios_base::out|ios_base::binary);

vector<span class="token operator">&lt;</span>Tag <span class="token operator">*</span><span class="token operator">&gt;</span><span class="token double-colon punctuation">::</span>iterator it_tag<span class="token punctuation">;</span>
<span class="token keyword">for</span> <span class="token punctuation">(</span>it_tag <span class="token operator">=</span> _vpTag<span class="token punctuation">.</span><span class="token function">begin</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> it_tag <span class="token operator">!=</span> _vpTag<span class="token punctuation">.</span><span class="token function">end</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> it_tag<span class="token operator">++</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nType <span class="token operator">!=</span> <span class="token number">0x09</span><span class="token punctuation">)</span>
        <span class="token keyword">continue</span><span class="token punctuation">;</span>

    f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pMedia<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_nMediaLen<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>
f<span class="token punctuation">.</span><span class="token function">close</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">return</span> <span class="token number">1</span><span class="token punctuation">;</span>

}

int CFlvParser::DumpAAC(const std::string &path)
{
fstream f;
f.open(path.c_str(), ios_base::out | ios_base::binary);

vector<span class="token operator">&lt;</span>Tag <span class="token operator">*</span><span class="token operator">&gt;</span><span class="token double-colon punctuation">::</span>iterator it_tag<span class="token punctuation">;</span>
<span class="token keyword">for</span> <span class="token punctuation">(</span>it_tag <span class="token operator">=</span> _vpTag<span class="token punctuation">.</span><span class="token function">begin</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> it_tag <span class="token operator">!=</span> _vpTag<span class="token punctuation">.</span><span class="token function">end</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> it_tag<span class="token operator">++</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nType <span class="token operator">!=</span> <span class="token number">0x08</span><span class="token punctuation">)</span>
        <span class="token keyword">continue</span><span class="token punctuation">;</span>

    CAudioTag <span class="token operator">*</span>pAudioTag <span class="token operator">=</span> <span class="token punctuation">(</span>CAudioTag <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token keyword">if</span> <span class="token punctuation">(</span>pAudioTag<span class="token operator">-&gt;</span>_nSoundFormat <span class="token operator">!=</span> <span class="token number">10</span><span class="token punctuation">)</span>
        <span class="token keyword">continue</span><span class="token punctuation">;</span>

    <span class="token keyword">if</span> <span class="token punctuation">(</span>pAudioTag<span class="token operator">-&gt;</span>_nMediaLen<span class="token operator">!=</span><span class="token number">0</span><span class="token punctuation">)</span>
        f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pMedia<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_nMediaLen<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>
f<span class="token punctuation">.</span><span class="token function">close</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">return</span> <span class="token number">1</span><span class="token punctuation">;</span>

}

int CFlvParser::DumpFlv(const std::string &path)
{
fstream f;
f.open(path.c_str(), ios_base::out | ios_base::binary);

<span class="token comment">// write flv-header</span>
f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span>_pFlvHeader<span class="token operator">-&gt;</span>pFlvHeader<span class="token punctuation">,</span> _pFlvHeader<span class="token operator">-&gt;</span>nHeadSize<span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">uint32_t</span> nLastTagSize <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>


<span class="token comment">// write flv-tag</span>
vector<span class="token operator">&lt;</span>Tag <span class="token operator">*</span><span class="token operator">&gt;</span><span class="token double-colon punctuation">::</span>iterator it_tag<span class="token punctuation">;</span>
<span class="token keyword">for</span> <span class="token punctuation">(</span>it_tag <span class="token operator">=</span> _vpTag<span class="token punctuation">.</span><span class="token function">begin</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> it_tag <span class="token operator">&lt;</span> _vpTag<span class="token punctuation">.</span><span class="token function">end</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> it_tag<span class="token operator">++</span><span class="token punctuation">)</span>
<span class="token punctuation">{<!-- --></span>
    <span class="token keyword">uint32_t</span> nn <span class="token operator">=</span> <span class="token function">WriteU32</span><span class="token punctuation">(</span>nLastTagSize<span class="token punctuation">)</span><span class="token punctuation">;</span>
    f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token operator">&amp;</span>nn<span class="token punctuation">,</span> <span class="token number">4</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

    <span class="token comment">//check duplicate start code</span>
    <span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nType <span class="token operator">==</span> <span class="token number">0x09</span> <span class="token operator">&amp;&amp;</span> <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">1</span><span class="token punctuation">)</span> <span class="token operator">==</span> <span class="token number">0x01</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        <span class="token keyword">bool</span> duplicate <span class="token operator">=</span> <span class="token boolean">false</span><span class="token punctuation">;</span>
        <span class="token keyword">uint8_t</span> <span class="token operator">*</span>pStartCode <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span> <span class="token operator">+</span> _nNalUnitLength<span class="token punctuation">;</span>
        <span class="token comment">//printf("tagsize=%d\n",(*it_tag)-&gt;_header.nDataSize);</span>
        <span class="token keyword">unsigned</span> nalu_len <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span>
        <span class="token keyword">uint8_t</span> <span class="token operator">*</span>p_nalu_len<span class="token operator">=</span><span class="token punctuation">(</span><span class="token keyword">uint8_t</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token operator">&amp;</span>nalu_len<span class="token punctuation">;</span>
        <span class="token keyword">switch</span> <span class="token punctuation">(</span>_nNalUnitLength<span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
        <span class="token keyword">case</span> <span class="token number">4</span><span class="token operator">:</span>
            nalu_len <span class="token operator">=</span> <span class="token function">ShowU32</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token keyword">break</span><span class="token punctuation">;</span>
        <span class="token keyword">case</span> <span class="token number">3</span><span class="token operator">:</span>
            nalu_len <span class="token operator">=</span> <span class="token function">ShowU24</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token keyword">break</span><span class="token punctuation">;</span>
        <span class="token keyword">case</span> <span class="token number">2</span><span class="token operator">:</span>
            nalu_len <span class="token operator">=</span> <span class="token function">ShowU16</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token keyword">break</span><span class="token punctuation">;</span>
        <span class="token keyword">default</span><span class="token operator">:</span>
            nalu_len <span class="token operator">=</span> <span class="token function">ShowU8</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token keyword">break</span><span class="token punctuation">;</span>
        <span class="token punctuation">}</span>
        <span class="token comment">/*
        printf("nalu_len=%u\n",nalu_len);
        printf("%x,%x,%x,%x,%x,%x,%x,%x,%x\n",(*it_tag)-&gt;_pTagData[5],(*it_tag)-&gt;_pTagData[6],
                (*it_tag)-&gt;_pTagData[7],(*it_tag)-&gt;_pTagData[8],(*it_tag)-&gt;_pTagData[9],
                (*it_tag)-&gt;_pTagData[10],(*it_tag)-&gt;_pTagData[11],(*it_tag)-&gt;_pTagData[12],
                (*it_tag)-&gt;_pTagData[13]);
        */</span>

        <span class="token keyword">uint8_t</span> <span class="token operator">*</span>pStartCodeRecord <span class="token operator">=</span> pStartCode<span class="token punctuation">;</span>
        <span class="token keyword">int</span> i<span class="token punctuation">;</span>
        <span class="token keyword">for</span> <span class="token punctuation">(</span>i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize <span class="token operator">-</span> <span class="token number">5</span> <span class="token operator">-</span> _nNalUnitLength <span class="token operator">-</span> <span class="token number">4</span><span class="token punctuation">;</span> <span class="token operator">++</span>i<span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
            <span class="token keyword">if</span> <span class="token punctuation">(</span>pStartCode<span class="token punctuation">[</span>i<span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x00</span> <span class="token operator">&amp;&amp;</span> pStartCode<span class="token punctuation">[</span>i<span class="token operator">+</span><span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x00</span> <span class="token operator">&amp;&amp;</span> pStartCode<span class="token punctuation">[</span>i<span class="token operator">+</span><span class="token number">2</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x00</span> <span class="token operator">&amp;&amp;</span>
                    pStartCode<span class="token punctuation">[</span>i<span class="token operator">+</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x01</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
                <span class="token keyword">if</span> <span class="token punctuation">(</span>pStartCode<span class="token punctuation">[</span>i<span class="token operator">+</span><span class="token number">4</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x67</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
                    <span class="token comment">//printf("duplicate sps found!\n");</span>
                    i <span class="token operator">+=</span> <span class="token number">4</span><span class="token punctuation">;</span>
                    <span class="token keyword">continue</span><span class="token punctuation">;</span>
                <span class="token punctuation">}</span>
                <span class="token keyword">else</span> <span class="token keyword">if</span> <span class="token punctuation">(</span>pStartCode<span class="token punctuation">[</span>i<span class="token operator">+</span><span class="token number">4</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x68</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
                    <span class="token comment">//printf("duplicate pps found!\n");</span>
                    i <span class="token operator">+=</span> <span class="token number">4</span><span class="token punctuation">;</span>
                    <span class="token keyword">continue</span><span class="token punctuation">;</span>
                <span class="token punctuation">}</span>
                <span class="token keyword">else</span> <span class="token keyword">if</span> <span class="token punctuation">(</span>pStartCode<span class="token punctuation">[</span>i<span class="token operator">+</span><span class="token number">4</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x06</span><span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
                    <span class="token comment">//printf("duplicate sei found!\n");</span>
                    i <span class="token operator">+=</span> <span class="token number">4</span><span class="token punctuation">;</span>
                    <span class="token keyword">continue</span><span class="token punctuation">;</span>
                <span class="token punctuation">}</span>
                <span class="token keyword">else</span> <span class="token punctuation">{<!-- --></span>
                    i <span class="token operator">+=</span> <span class="token number">4</span><span class="token punctuation">;</span>
                    <span class="token comment">//printf("offset=%d\n",i);</span>
                    duplicate <span class="token operator">=</span> <span class="token boolean">true</span><span class="token punctuation">;</span>
                    <span class="token keyword">break</span><span class="token punctuation">;</span>
                <span class="token punctuation">}</span>
            <span class="token punctuation">}</span>
        <span class="token punctuation">}</span>

        <span class="token keyword">if</span> <span class="token punctuation">(</span>duplicate<span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
            nalu_len <span class="token operator">-=</span> i<span class="token punctuation">;</span>
            <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize <span class="token operator">-=</span> i<span class="token punctuation">;</span>
            <span class="token keyword">uint8_t</span> <span class="token operator">*</span>p <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token keyword">uint8_t</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token operator">&amp;</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize<span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagHeader<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span> <span class="token operator">=</span> p<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
            <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagHeader<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span> <span class="token operator">=</span> p<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
            <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagHeader<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span> <span class="token operator">=</span> p<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
            <span class="token comment">//printf("after,tagsize=%d\n",(int)ShowU24((*it_tag)-&gt;_pTagHeader + 1));</span>
            <span class="token comment">//printf("%x,%x,%x\n",(*it_tag)-&gt;_pTagHeader[1],(*it_tag)-&gt;_pTagHeader[2],(*it_tag)-&gt;_pTagHeader[3]);</span>

            f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagHeader<span class="token punctuation">,</span> <span class="token number">11</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token keyword">switch</span> <span class="token punctuation">(</span>_nNalUnitLength<span class="token punctuation">)</span> <span class="token punctuation">{<!-- --></span>
            <span class="token keyword">case</span> <span class="token number">4</span><span class="token operator">:</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">3</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">6</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">7</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">8</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token keyword">break</span><span class="token punctuation">;</span>
            <span class="token keyword">case</span> <span class="token number">3</span><span class="token operator">:</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">6</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">7</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token keyword">break</span><span class="token punctuation">;</span>
            <span class="token keyword">case</span> <span class="token number">2</span><span class="token operator">:</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">6</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token keyword">break</span><span class="token punctuation">;</span>
            <span class="token keyword">default</span><span class="token operator">:</span>
                <span class="token operator">*</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData <span class="token operator">+</span> <span class="token number">5</span><span class="token punctuation">)</span> <span class="token operator">=</span> p_nalu_len<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span><span class="token punctuation">;</span>
                <span class="token keyword">break</span><span class="token punctuation">;</span>
            <span class="token punctuation">}</span>
            <span class="token comment">//printf("after,nalu_len=%d\n",(int)ShowU32((*it_tag)-&gt;_pTagData + 5));</span>
            f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData<span class="token punctuation">,</span> pStartCode <span class="token operator">-</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData<span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token comment">/*
            printf("%x,%x,%x,%x,%x,%x,%x,%x,%x\n",(*it_tag)-&gt;_pTagData[0],(*it_tag)-&gt;_pTagData[1],(*it_tag)-&gt;_pTagData[2],
                    (*it_tag)-&gt;_pTagData[3],(*it_tag)-&gt;_pTagData[4],(*it_tag)-&gt;_pTagData[5],(*it_tag)-&gt;_pTagData[6],
                    (*it_tag)-&gt;_pTagData[7],(*it_tag)-&gt;_pTagData[8]);
            */</span>
            f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span>pStartCode <span class="token operator">+</span> i<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize <span class="token operator">-</span> <span class="token punctuation">(</span>pStartCode <span class="token operator">-</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData<span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            <span class="token comment">/*
            printf("write size:%d\n", (pStartCode - (*it_tag)-&gt;_pTagData) +
                    ((*it_tag)-&gt;_header.nDataSize - (pStartCode - (*it_tag)-&gt;_pTagData)));
            */</span>
        <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token punctuation">{<!-- --></span>
            f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagHeader<span class="token punctuation">,</span> <span class="token number">11</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
            f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize<span class="token punctuation">)</span><span class="token punctuation">;</span>
        <span class="token punctuation">}</span>
    <span class="token punctuation">}</span> <span class="token keyword">else</span> <span class="token punctuation">{<!-- --></span>
        f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagHeader<span class="token punctuation">,</span> <span class="token number">11</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
        f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_pTagData<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize<span class="token punctuation">)</span><span class="token punctuation">;</span>
    <span class="token punctuation">}</span>

    nLastTagSize <span class="token operator">=</span> <span class="token number">11</span> <span class="token operator">+</span> <span class="token punctuation">(</span><span class="token operator">*</span>it_tag<span class="token punctuation">)</span><span class="token operator">-&gt;</span>_header<span class="token punctuation">.</span>nDataSize<span class="token punctuation">;</span>
<span class="token punctuation">}</span>
<span class="token keyword">uint32_t</span> nn <span class="token operator">=</span> <span class="token function">WriteU32</span><span class="token punctuation">(</span>nLastTagSize<span class="token punctuation">)</span><span class="token punctuation">;</span>
f<span class="token punctuation">.</span><span class="token function">write</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token keyword">char</span> <span class="token operator">*</span><span class="token punctuation">)</span><span class="token operator">&amp;</span>nn<span class="token punctuation">,</span> <span class="token number">4</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

f<span class="token punctuation">.</span><span class="token function">close</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token keyword">return</span> <span class="token number">1</span><span class="token punctuation">;</span>

}

int CFlvParser::Stat()
{
for (int i = 0; i < _vpTag.size(); i++)
{
switch (_vpTag[i]->_header.nType)
{
case 0x08:
_sStat.nAudioNum++;
break;
case 0x09:
StatVideo(_vpTag[i]);
break;
case 0x12:
_sStat.nMetaNum++;
break;
default:
;
}
}

<span class="token keyword">return</span> <span class="token number">1</span><span class="token punctuation">;</span>

}

int CFlvParser::StatVideo(Tag *pTag)
{
_sStat.nVideoNum++;
_sStat.nMaxTimeStamp = pTag->_header.nTimeStamp;

<span class="token keyword">if</span> <span class="token punctuation">(</span>pTag<span class="token operator">-&gt;</span>_pTagData<span class="token punctuation">[</span><span class="token number">0</span><span class="token punctuation">]</span> <span class="token operator">==</span> <span class="token number">0x17</span> <span class="token operator">&amp;&amp;</span> pTag<span class="token operator">-&gt;</span>_pTagDat
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值