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

📄 ts.c

📁 VLC Player Source Code
💻 C
📖 第 1 页 / 共 5 页
字号:
            *pi64 = p_sys->i_time;            return VLC_SUCCESS;        case DEMUX_GET_LENGTH:            pi64 = (int64_t*)va_arg( args, int64_t * );            if( p_sys->i_mux_rate > 0 )            {                *pi64 = INT64_C(1000000) * ( stream_Size( p_demux->s ) / 50 ) /                        p_sys->i_mux_rate;                return VLC_SUCCESS;            }            *pi64 = 0;            return VLC_EGENERIC;#else        case DEMUX_GET_TIME:            pi64 = (int64_t*)va_arg( args, int64_t * );            if( DVBEventInformation( p_demux, pi64, NULL ) )                *pi64 = 0;            return VLC_SUCCESS;        case DEMUX_GET_LENGTH:            pi64 = (int64_t*)va_arg( args, int64_t * );            if( DVBEventInformation( p_demux, NULL, pi64 ) )                *pi64 = 0;            return VLC_SUCCESS;#endif        case DEMUX_SET_GROUP:        {            uint16_t i_vpid = 0, i_apid1 = 0, i_apid2 = 0, i_apid3 = 0;            ts_prg_psi_t *p_prg = NULL;            vlc_list_t *p_list;            i_int = (int)va_arg( args, int );            p_list = (vlc_list_t *)va_arg( args, vlc_list_t * );            msg_Dbg( p_demux, "DEMUX_SET_GROUP %d %p", i_int, p_list );            if( p_sys->b_dvb_control && i_int > 0 && i_int != p_sys->i_dvb_program )            {                int i_pmt_pid = -1;                int i;                /* Search pmt to be unselected */                for( i = 0; i < p_sys->i_pmt; i++ )                {                    ts_pid_t *pmt = p_sys->pmt[i];                    int i_prg;                    for( i_prg = 0; i_prg < pmt->psi->i_prg; i_prg++ )                    {                        if( pmt->psi->prg[i_prg]->i_number == p_sys->i_dvb_program )                        {                            i_pmt_pid = p_sys->pmt[i]->i_pid;                            break;                        }                    }                    if( i_pmt_pid > 0 ) break;                }                if( i_pmt_pid > 0 )                {                    stream_Control( p_demux->s, STREAM_CONTROL_ACCESS,                                    ACCESS_SET_PRIVATE_ID_STATE, i_pmt_pid,                                    false );                    /* All ES */                    for( i = 2; i < 8192; i++ )                    {                        ts_pid_t *pid = &p_sys->pid[i];                        int i_prg;                        if( !pid->b_valid || pid->psi ) continue;                        for( i_prg = 0; i_prg < pid->p_owner->i_prg; i_prg++ )                        {                            if( pid->p_owner->prg[i_prg]->i_pid_pmt == i_pmt_pid && pid->es->id )                            {                                /* We only remove es that aren't defined by extra pmt */                                stream_Control( p_demux->s,                                                STREAM_CONTROL_ACCESS,                                                ACCESS_SET_PRIVATE_ID_STATE,                                                i, false );                                break;                            }                        }                    }                }                /* select new program */                p_sys->i_dvb_program = i_int;                i_pmt_pid = -1;                for( i = 0; i < p_sys->i_pmt; i++ )                {                    ts_pid_t *pmt = p_sys->pmt[i];                    int i_prg;                    for( i_prg = 0; i_prg < pmt->psi->i_prg; i_prg++ )                    {                        if( pmt->psi->prg[i_prg]->i_number == i_int )                        {                            i_pmt_pid = p_sys->pmt[i]->i_pid;                            p_prg = p_sys->pmt[i]->psi->prg[i_prg];                            break;                        }                    }                    if( i_pmt_pid > 0 ) break;                }                if( i_pmt_pid > 0 )                {                    stream_Control( p_demux->s, STREAM_CONTROL_ACCESS,                                    ACCESS_SET_PRIVATE_ID_STATE, i_pmt_pid,                                    true );                    stream_Control( p_demux->s, STREAM_CONTROL_ACCESS,                                    ACCESS_SET_PRIVATE_ID_STATE, p_prg->i_pid_pcr,                                    true );                    for( i = 2; i < 8192; i++ )                    {                        ts_pid_t *pid = &p_sys->pid[i];                        int i_prg;                        if( !pid->b_valid || pid->psi ) continue;                        for( i_prg = 0; i_prg < pid->p_owner->i_prg; i_prg++ )                        {                            if( pid->p_owner->prg[i_prg]->i_pid_pmt == i_pmt_pid && pid->es->id )                            {                                if ( pid->es->fmt.i_cat == VIDEO_ES && !i_vpid )                                    i_vpid = i;                                if ( pid->es->fmt.i_cat == AUDIO_ES && !i_apid1 )                                    i_apid1 = i;                                else if ( pid->es->fmt.i_cat == AUDIO_ES && !i_apid2 )                                    i_apid2 = i;                                else if ( pid->es->fmt.i_cat == AUDIO_ES && !i_apid3 )                                    i_apid3 = i;                                stream_Control( p_demux->s,                                                STREAM_CONTROL_ACCESS,                                                ACCESS_SET_PRIVATE_ID_STATE,                                                i, true );                                break;                            }                        }                    }                }            }            else            {                p_sys->i_dvb_program = -1;                p_sys->p_programs_list = p_list;            }            return VLC_SUCCESS;        }        case DEMUX_GET_FPS:        case DEMUX_SET_TIME:        default:            return VLC_EGENERIC;    }}/***************************************************************************** * *****************************************************************************/static int UserPmt( demux_t *p_demux, const char *psz_fmt ){    demux_sys_t *p_sys = p_demux->p_sys;    char *psz_dup = strdup( psz_fmt );    char *psz = psz_dup;    int  i_pid;    int  i_number;    if( !psz_dup )        return VLC_ENOMEM;    /* Parse PID */    i_pid = strtol( psz, &psz, 0 );    if( i_pid < 2 || i_pid >= 8192 )        goto error;    /* Parse optional program number */    i_number = 0;    if( *psz == ':' )        i_number = strtol( &psz[1], &psz, 0 );    /* */    ts_pid_t *pmt = &p_sys->pid[i_pid];    ts_prg_psi_t *prg;    msg_Dbg( p_demux, "user pmt specified (pid=%d,number=%d)", i_pid, i_number );    PIDInit( pmt, true, NULL );    /* Dummy PMT */    prg = malloc( sizeof( ts_prg_psi_t ) );    if( !prg )        goto error;    memset( prg, 0, sizeof( ts_prg_psi_t ) );    prg->i_pid_pcr  = -1;    prg->i_pid_pmt  = -1;    prg->i_version  = -1;    prg->i_number   = i_number != 0 ? i_number : TS_USER_PMT_NUMBER;    prg->handle     = dvbpsi_AttachPMT( i_number != TS_USER_PMT_NUMBER ? i_number : 1, (dvbpsi_pmt_callback)PMTCallBack, p_demux );    TAB_APPEND( pmt->psi->i_prg, pmt->psi->prg, prg );    psz = strchr( psz, '=' );    if( psz )        psz++;    while( psz && *psz )    {        char *psz_next = strchr( psz, ',' );        int i_pid;        if( psz_next )            *psz_next++ = '\0';        i_pid = strtol( psz, &psz, 0 );        if( *psz != ':' || i_pid < 2 || i_pid >= 8192 )            goto next;        char *psz_opt = &psz[1];        if( !strcmp( psz_opt, "pcr" ) )        {            prg->i_pid_pcr = i_pid;        }        else if( !p_sys->pid[i_pid].b_valid )        {            ts_pid_t *pid = &p_sys->pid[i_pid];            char *psz_arg = strchr( psz_opt, '=' );            if( psz_arg )                *psz_arg++ = '\0';            PIDInit( pid, false, pmt->psi);            if( prg->i_pid_pcr <= 0 )                prg->i_pid_pcr = i_pid;            if( psz_arg && strlen( psz_arg ) == 4 )            {                const vlc_fourcc_t i_codec = VLC_FOURCC( psz_arg[0], psz_arg[1],                                                         psz_arg[2], psz_arg[3] );                int i_cat = UNKNOWN_ES;                es_format_t *fmt = &pid->es->fmt;                if( !strcmp( psz_opt, "video" ) )                    i_cat = VIDEO_ES;                else if( !strcmp( psz_opt, "audio" ) )                    i_cat = AUDIO_ES;                else if( !strcmp( psz_opt, "spu" ) )                    i_cat = SPU_ES;                es_format_Init( fmt, i_cat, i_codec );                fmt->b_packetized = false;            }            else            {                const int i_stream_type = strtol( psz_opt, NULL, 0 );                PIDFillFormat( pid, i_stream_type );            }            pid->es->fmt.i_group = i_number;            if( p_sys->b_es_id_pid )                pid->es->fmt.i_id = i_pid;            if( pid->es->fmt.i_cat != UNKNOWN_ES )            {                msg_Dbg( p_demux, "  * es pid=%d fcc=%4.4s", i_pid,                         (char*)&pid->es->fmt.i_codec );                pid->es->id = es_out_Add( p_demux->out,                                          &pid->es->fmt );            }        }    next:        psz = psz_next;    }    p_sys->b_user_pmt = true;    TAB_APPEND( p_sys->i_pmt, p_sys->pmt, pmt );    free( psz_dup );    return VLC_SUCCESS;error:    free( psz_dup );    return VLC_EGENERIC;}static void PIDInit( ts_pid_t *pid, bool b_psi, ts_psi_t *p_owner ){    bool b_old_valid = pid->b_valid;    pid->b_valid    = true;    pid->i_cc       = 0xff;    pid->p_owner    = p_owner;    pid->i_owner_number = 0;    TAB_INIT( pid->i_extra_es, pid->extra_es );    if( b_psi )    {        pid->es  = NULL;        if( !b_old_valid )        {            free( pid->psi );            pid->psi = malloc( sizeof( ts_psi_t ) );            if( pid->psi )            {                pid->psi->handle= NULL;                pid->psi->i_prg = 0;                pid->psi->prg   = NULL;            }        }        pid->psi->i_pat_version  = -1;        pid->psi->i_sdt_version  = -1;        if( p_owner )        {            ts_prg_psi_t *prg = malloc( sizeof( ts_prg_psi_t ) );            if( prg )            {                /* PMT */                prg->i_version  = -1;                prg->i_number   = -1;                prg->i_pid_pcr  = -1;                prg->i_pid_pmt  = -1;                prg->iod        = NULL;                prg->handle     = NULL;                TAB_APPEND( pid->psi->i_prg, pid->psi->prg, prg );            }        }    }    else    {        pid->psi = NULL;        pid->es  = malloc( sizeof( ts_es_t ) );        if( pid->es )        {            es_format_Init( &pid->es->fmt, UNKNOWN_ES, 0 );            pid->es->id      = NULL;            pid->es->p_pes   = NULL;            pid->es->i_pes_size= 0;            pid->es->i_pes_gathered= 0;            pid->es->pp_last = &pid->es->p_pes;            pid->es->p_mpeg4desc = NULL;            pid->es->b_gather = false;        }    }}static void PIDClean( es_out_t *out, ts_pid_t *pid ){    if( pid->psi )    {        int i;        if( pid->psi->handle ) dvbpsi_DetachPMT( pid->psi->handle );        for( i = 0; i < pid->psi->i_prg; i++ )        {            if( pid->psi->prg[i]->iod )                IODFree( pid->psi->prg[i]->iod );            if( pid->psi->prg[i]->handle )                dvbpsi_DetachPMT( pid->psi->prg[i]->handle );            free( pid->psi->prg[i] );        }        free( pid->psi->prg );        free( pid->psi );    }    else    {        int i;        if( pid->es->id )            es_out_Del( out, pid->es->id );        if( pid->es->p_pes )            block_ChainRelease( pid->es->p_pes );        es_format_Clean( &pid->es->fmt );        free( pid->es );        for( i = 0; i < pid->i_extra_es; i++ )        {            if( pid->extra_es[i]->id )                es_out_Del( out, pid->extra_es[i]->id );            if( pid->extra_es[i]->p_pes )                block_ChainRelease( pid->extra_es[i]->p_pes );            es_format_Clean( &pid->extra_es[i]->fmt );            free( pid->extra_es[i] );        }        if( pid->i_extra_es ) free( pid->extra_es );    }    pid->b_valid = false;}/**************************************************************************** * gathering stuff ****************************************************************************/static void ParsePES( demux_t *p_demux, ts_pid_t *pid ){    block_t *p_pes = pid->es->p_pes;    uint8_t header[30];    int     i_pes_size = 0;    int     i_skip = 0;    mtime_t i_dts = -1;    mtime_t i_pts = -1;    mtime_t i_length = 0;    int i_max;    /* remove the pes from pid */

⌨️ 快捷键说明

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