⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 input_file.c

📁 vlc stand 0.1.99 ist sehr einfach
💻 C
📖 第 1 页 / 共 3 页
字号:
/***************************************************************************** * input_file.c: functions to read from a file ***************************************************************************** * Copyright (C) 1999, 2000 VideoLAN * * Authors: * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. *  * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111, USA. *****************************************************************************//***************************************************************************** * Preamble *****************************************************************************/#include "defs.h"#include <stdio.h>#include <unistd.h>                                               /* close() */#include <sys/types.h>                        /* on BSD, uio.h needs types.h */#include <sys/uio.h>                                            /* "input.h" */#include <sys/stat.h>                                    /* fstat, off_t ... */#include <netinet/in.h>                                           /* ntohl() */#include <fcntl.h>                                                 /* open() */#include <malloc.h>                                      /* malloc, read ... */#include <string.h>#include "config.h"#include "common.h"#include "threads.h"#include "mtime.h"#include "intf_msg.h"#include "main.h"#include "input.h"#include "input_ps.h"#include "input_file.h"#define BUF_SIZE (797*3)#define PS_METHOD 1#define TS_METHOD 2#define TS_PACKET_SIZE 188#define TS_IN_UDP 7#define MAX_AUDIO_CHANNEL 15#define MAX_SUBTITLES_CHANNEL 31#define NO_SUBTITLES 255#define PS_BUFFER_SIZE 16384#define NO_PES 0#define AUDIO_PES 1#define VIDEO_PES 2#define AC3_PES 3#define SUBTITLE_PES 4#define LPCM_PES 5#define PRIVATE_PES 6#define UNKNOWN_PES 12#define PCR_PID 0x20 /* 0x20 == first video stream                      * 0x40 == first audio stream */typedef u8 file_ts_packet[TS_PACKET_SIZE];typedef file_ts_packet udp_packet[TS_IN_UDP];typedef struct synchro_struct{    mtime_t     delta_clock;    mtime_t     slope;    mtime_t     last_pcr_time;        file_ts_packet *last_pcr;} synchro_t;typedef struct in_data_s{    int start, end;    vlc_mutex_t lock;    vlc_cond_t notfull;    vlc_cond_t notempty;    udp_packet buf[BUF_SIZE+1];} in_data_t;typedef struct own_pcr_s{    int start, end;    vlc_mutex_t lock;    file_ts_packet *buf[(BUF_SIZE+1)*TS_IN_UDP+1];} own_pcr_t;typedef struct options_s{    unsigned int pcr_pid;    u8 i_file_type;    int in;     char **playlist;    int i_list_index;} options_t;typedef struct s_ps{    unsigned int pat_counter;    unsigned int pmt_counter;    /*     * These 3 parameters are passed      * as command line arguments     */    unsigned int audio_channel;    unsigned int subtitles_channel;    unsigned int audio_type;    /*      * 16 audio mpeg streams     * 16 audio AV3 streams     * 16 video mpeg streams     * 32 subtitle streams     */    unsigned int media_counter[0x100];    unsigned int association_table[0x100];    unsigned int found_streams;    unsigned int found_pts;    unsigned int ts_to_write;    unsigned int ts_written;    unsigned int sent_ts;    unsigned char *ps_data;    unsigned char *ps_end;    unsigned char *ps_buffer;    unsigned int pes_id;    unsigned int private_id;    unsigned int has_pts;    unsigned int pcr_pid;    unsigned int pes_type;    unsigned int pes_size;    unsigned int to_skip;    unsigned int offset;} ps_t;typedef struct input_file_s{    boolean_t    b_die; /* b_die flag for the disk thread */    vlc_thread_t disk_thread;    synchro_t    synchro;    ps_t         ps;    in_data_t    in_data;    options_t    options;    own_pcr_t    own_pcr;} input_file_t;/* local prototypes */void ps_fill( input_file_t * p_if, boolean_t wait );ssize_t safe_read(options_t *p_options, unsigned char *buf, int count);void input_DiskThread( input_file_t * p_if );int init_synchro( input_file_t * p_if );input_file_t input_file;/****************************************************************************** * ConvertPCRTime : extracts and converts the PCR time in microseconds ******************************************************************************/s64 ConvertPCRTime(file_ts_packet *pcr_buff){    return( (((((s64)U32_AT(((u8*)pcr_buff)+6)) << 1) | (((u8*)pcr_buff)[10] >> 7)) * 300) / 27 );}/****************************************************************************** * wait_a_moment : Compute how long we must wait before sending a TS packet ******************************************************************************/static void wait_a_moment( input_file_t * p_if, file_ts_packet *ts){    synchro_t * p_synchro = &input_file.synchro;        static int retard_count = 0;    static s64 wait_max = 0;    s64 sendtime; /* the date at which the TS packet should be sent */    s64 wait;        sendtime = p_synchro->last_pcr_time + p_synchro->delta_clock +        p_synchro->slope * ((ts - p_synchro->last_pcr + (BUF_SIZE+1)*TS_IN_UDP) % ((BUF_SIZE+1)*TS_IN_UDP));     wait = sendtime - mdate();    if( wait > 0 )    {         retard_count = 0;        if(wait > 100000)        {            intf_DbgMsg( "input warning: wait time may be too long : %Ld\n", wait );            return;        }        msleep( wait );    }    else    {        if( wait < wait_max )        {            wait_max = wait;        }        retard_count++;        if( retard_count == 16 )        {            retard_count = 0;        }    }}/****************************************************************************** * adjust : Adjust the encoder clock & remove the PCR from own_pcr ******************************************************************************/static void adjust( input_file_t * p_if, file_ts_packet *ts ){    synchro_t * p_synchro = &p_if->synchro;    own_pcr_t * p_own_pcr = &p_if->own_pcr;    file_ts_packet *next_pcr;    int no_discontinuity = 1;        if( ((u8*)ts)[5] & 0x80 )    {        /* There is a discontinuity - I recalculate the delta */        p_synchro->delta_clock = mdate() - ConvertPCRTime(ts);        intf_DbgMsg( "input warning: clock discontinuity\n" );        no_discontinuity = 0;    }    else    {        p_synchro->last_pcr = ts;        p_synchro->last_pcr_time = ConvertPCRTime( ts );    }            vlc_mutex_lock(&p_own_pcr->lock);    p_own_pcr->start++;    p_own_pcr->start %= (BUF_SIZE+1)*TS_IN_UDP+1;        /* If we have 2 consecutiv PCR, we can reevaluate slope */    if( (p_own_pcr->start != p_own_pcr->end) &&        no_discontinuity &&        !((((u8*) next_pcr = p_own_pcr->buf[p_own_pcr->start]))[5] & 0x80))    {        s64 current_pcr_time = ConvertPCRTime(ts);        s64 next_pcr_time =    ConvertPCRTime(next_pcr);                if( (next_pcr_time - current_pcr_time < 0) || (next_pcr_time - current_pcr_time > 700000))        {            intf_DbgMsg( "input warning: possible discontinuity\n" );            p_synchro->delta_clock = mdate() - next_pcr_time;        }        else        {            p_synchro->slope = (next_pcr_time - current_pcr_time) /                ((next_pcr - ts + (BUF_SIZE+1)*TS_IN_UDP) % ((BUF_SIZE+1)*TS_IN_UDP));        }    }        vlc_mutex_unlock(&p_own_pcr->lock);}/***************************************************************************** * file_next : Opens the next available file *****************************************************************************/int file_next( options_t *options ){    /* the check for index == 0 should be done _before_ */    options->i_list_index--;        if( options->in != -1 )    {            close( options->in );    }    if( !strcmp( options->playlist[options->i_list_index], "-" ) )    {        /* read stdin */        return ( options->in = 0 );    }    else    {        /* read the actual file */        fprintf( stderr, "Playing file %s\n",                 options->playlist[options->i_list_index] );        return ( options->in = open( options->playlist[options->i_list_index],                                     O_RDONLY | O_NDELAY ) );    }}/***************************************************************************** * safe_read : Buffered reading method *****************************************************************************/ssize_t safe_read( options_t *options, unsigned char *buf, int count ){    int ret, cnt=0;        while( cnt < count )    {        ret = read( options->in, buf + cnt, count - cnt );            if( ret < 0 )            return ret;            if( ret == 0 )        {            /* zero means end of file */            if( options->i_list_index )            {                file_next( options );            }            else            {                break;            }        }            cnt += ret;    }    return cnt;}/****************************************************************************** * keep_pcr : Put a TS packet in the fifo if it owns a PCR ******************************************************************************/int keep_pcr(int pcr_pid, file_ts_packet *ts){    own_pcr_t * p_own_pcr =   &input_file.own_pcr;#define p ((u8 *)ts)    if ((p[3] & 0x20) && p[4] && (p[5] & 0x10)        && ((((p[1]<<8)+p[2]) & 0x1FFF) == pcr_pid))    {        /* adaptation_field_control is set, adaptation_field_lenght is not 0,         * PCR_flag is set, pid == pcr_pid */        vlc_mutex_lock(&p_own_pcr->lock);        p_own_pcr->buf[p_own_pcr->end++] = ts;        p_own_pcr->end %= (BUF_SIZE+1)*TS_IN_UDP+1;        vlc_mutex_unlock(&p_own_pcr->lock);        return 1;    }     else        return 0;#undef p}/****************************************************************************** * get_pid : gets a pid from a PES type ******************************************************************************/int get_pid (ps_t *p_ps){    int i, tofind, delta;    char* type;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -