mirror of
https://github.com/mpv-player/mpv.git
synced 2024-09-20 12:02:23 +02:00
AVI demuxer cleanups, fileformat-dependent stuff moved to priv_t
git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@1486 b3059339-0415-0410-9bf9-f77b7e298cf2
This commit is contained in:
parent
5a09680795
commit
610912b8b5
24
asf.h
24
asf.h
@ -156,12 +156,36 @@ typedef enum {
|
||||
(h)->comment_size = le2me_16((h)->comment_size); \
|
||||
(h)->rating_size = le2me_16((h)->rating_size); \
|
||||
}
|
||||
#define le2me_BITMAPINFOHEADER(h) { \
|
||||
(h)->biSize = le2me_32((h)->biSize); \
|
||||
(h)->biWidth = le2me_32((h)->biWidth); \
|
||||
(h)->biHeight = le2me_32((h)->biHeight); \
|
||||
(h)->biPlanes = le2me_16((h)->biPlanes); \
|
||||
(h)->biBitCount = le2me_16((h)->biBitCount); \
|
||||
(h)->biCompression = le2me_32((h)->biCompression); \
|
||||
(h)->biSizeImage = le2me_32((h)->biSizeImage); \
|
||||
(h)->biXPelsPerMeter = le2me_32((h)->biXPelsPerMeter); \
|
||||
(h)->biYPelsPerMeter = le2me_32((h)->biYPelsPerMeter); \
|
||||
(h)->biClrUsed = le2me_32((h)->biClrUsed); \
|
||||
(h)->biClrImportant = le2me_32((h)->biClrImportant); \
|
||||
}
|
||||
#define le2me_WAVEFORMATEX(h) { \
|
||||
(h)->wFormatTag = le2me_16((h)->wFormatTag); \
|
||||
(h)->nChannels = le2me_16((h)->nChannels); \
|
||||
(h)->nSamplesPerSec = le2me_32((h)->nSamplesPerSec); \
|
||||
(h)->nAvgBytesPerSec = le2me_32((h)->nAvgBytesPerSec); \
|
||||
(h)->nBlockAlign = le2me_16((h)->nBlockAlign); \
|
||||
(h)->wBitsPerSample = le2me_16((h)->wBitsPerSample); \
|
||||
(h)->cbSize = le2me_16((h)->cbSize); \
|
||||
}
|
||||
#else
|
||||
#define le2me_ASF_obj_header_t(h) /**/
|
||||
#define le2me_ASF_header_t(h) /**/
|
||||
#define le2me_ASF_stream_header_t(h) /**/
|
||||
#define le2me_ASF_file_header_t(h) /**/
|
||||
#define le2me_ASF_content_description_t(h) /**/
|
||||
#define le2me_BITMAPINFOHEADER(h) /**/
|
||||
#define le2me_WAVEFORMATEX(h) /**/
|
||||
#endif
|
||||
|
||||
|
||||
|
@ -16,7 +16,7 @@ extern int verbose; // defined in mplayer.c
|
||||
|
||||
#include "codec-cfg.h"
|
||||
#include "stheader.h"
|
||||
#include "aviheader.h"
|
||||
//#include "aviheader.h"
|
||||
#include "asf.h"
|
||||
|
||||
#ifdef ARCH_X86
|
||||
|
47
aviheader.c
47
aviheader.c
@ -1,9 +1,10 @@
|
||||
|
||||
#include "config.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "config.h"
|
||||
|
||||
extern int verbose; // defined in mplayer.c
|
||||
|
||||
#include "stream.h"
|
||||
@ -35,9 +36,10 @@ sh_video_t *sh_video=NULL;
|
||||
int stream_id=-1;
|
||||
int idxfix_videostream=0;
|
||||
int idxfix_divx=0;
|
||||
avi_priv_t* priv=demuxer->priv;
|
||||
|
||||
//---- AVI header:
|
||||
demuxer->idx_size=0;
|
||||
priv->idx_size=0;
|
||||
while(1){
|
||||
int id=stream_read_dword_le(demuxer->stream);
|
||||
int chunksize,size2;
|
||||
@ -137,15 +139,15 @@ while(1){
|
||||
}
|
||||
case ckidAVINEWINDEX: if(index_mode){
|
||||
int i;
|
||||
demuxer->idx_size=size2>>4;
|
||||
priv->idx_size=size2>>4;
|
||||
if(verbose>=1) printf("Reading INDEX block, %d chunks for %ld frames\n",
|
||||
demuxer->idx_size,avih.dwTotalFrames);
|
||||
demuxer->idx=malloc(demuxer->idx_size<<4);
|
||||
stream_read(demuxer->stream,(char*)demuxer->idx,demuxer->idx_size<<4);
|
||||
for (i = 0; i < demuxer->idx_size; i++) // swap index to machine endian
|
||||
le2me_AVIINDEXENTRY((AVIINDEXENTRY*)demuxer->idx + i);
|
||||
chunksize-=demuxer->idx_size<<4;
|
||||
if(verbose>=2) print_index(demuxer->idx,demuxer->idx_size);
|
||||
priv->idx_size,avih.dwTotalFrames);
|
||||
priv->idx=malloc(priv->idx_size<<4);
|
||||
stream_read(demuxer->stream,(char*)priv->idx,priv->idx_size<<4);
|
||||
for (i = 0; i < priv->idx_size; i++) // swap index to machine endian
|
||||
le2me_AVIINDEXENTRY((AVIINDEXENTRY*)priv->idx + i);
|
||||
chunksize-=priv->idx_size<<4;
|
||||
if(verbose>=2) print_index(priv->idx,priv->idx_size);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -154,14 +156,14 @@ while(1){
|
||||
|
||||
}
|
||||
|
||||
if(index_mode>=2 || (demuxer->idx_size==0 && index_mode==1)){
|
||||
if(index_mode>=2 || (priv->idx_size==0 && index_mode==1)){
|
||||
// build index for file:
|
||||
stream_reset(demuxer->stream);
|
||||
stream_seek(demuxer->stream,demuxer->movi_start);
|
||||
|
||||
demuxer->idx_pos=0;
|
||||
demuxer->idx_size=0;
|
||||
demuxer->idx=NULL;
|
||||
priv->idx_pos=0;
|
||||
priv->idx_size=0;
|
||||
priv->idx=NULL;
|
||||
|
||||
while(1){
|
||||
int id,len,skip;
|
||||
@ -178,13 +180,13 @@ if(index_mode>=2 || (demuxer->idx_size==0 && index_mode==1)){
|
||||
if(stream_eof(demuxer->stream)) break;
|
||||
if(!id || avi_stream_id(id)==100) goto skip_chunk; // bad ID (or padding?)
|
||||
|
||||
if(demuxer->idx_pos<=demuxer->idx_size){
|
||||
// demuxer->idx_size+=32;
|
||||
demuxer->idx_size+=1024; // +16kB
|
||||
demuxer->idx=realloc(demuxer->idx,demuxer->idx_size*sizeof(AVIINDEXENTRY));
|
||||
if(!demuxer->idx){demuxer->idx_pos=0; break;} // error!
|
||||
if(priv->idx_pos<=priv->idx_size){
|
||||
// priv->idx_size+=32;
|
||||
priv->idx_size+=1024; // +16kB
|
||||
priv->idx=realloc(priv->idx,priv->idx_size*sizeof(AVIINDEXENTRY));
|
||||
if(!priv->idx){priv->idx_pos=0; break;} // error!
|
||||
}
|
||||
idx=&((AVIINDEXENTRY *)demuxer->idx)[demuxer->idx_pos++];
|
||||
idx=&((AVIINDEXENTRY *)priv->idx)[priv->idx_pos++];
|
||||
idx->ckid=id;
|
||||
idx->dwFlags=AVIIF_KEYFRAME; // FIXME
|
||||
idx->dwChunkOffset=demuxer->filepos;
|
||||
@ -212,11 +214,12 @@ skip_chunk:
|
||||
skip=(len+1)&(~1); // total bytes in this chunk
|
||||
stream_seek(demuxer->stream,8+demuxer->filepos+skip);
|
||||
}
|
||||
demuxer->idx_size=demuxer->idx_pos;
|
||||
printf("AVI: Generated index table for %d chunks!\n",demuxer->idx_size);
|
||||
priv->idx_size=priv->idx_pos;
|
||||
printf("AVI: Generated index table for %d chunks!\n",priv->idx_size);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#undef MIN
|
||||
|
||||
|
||||
|
23
aviheader.h
23
aviheader.h
@ -1,7 +1,7 @@
|
||||
#ifndef _aviheader_h
|
||||
#define _aviheader_h
|
||||
|
||||
#include "config.h" /* get correct definition WORDS_BIGENDIAN */
|
||||
//#include "config.h" /* get correct definition WORDS_BIGENDIAN */
|
||||
#include "bswap.h"
|
||||
|
||||
/*
|
||||
@ -83,3 +83,24 @@
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
typedef struct {
|
||||
// index stuff:
|
||||
void* idx;
|
||||
int idx_size;
|
||||
int idx_pos;
|
||||
int idx_pos_a;
|
||||
int idx_pos_v;
|
||||
int idx_offset; // ennyit kell hozzaadni az index offset ertekekhez
|
||||
// interleaved PTS stuff:
|
||||
int skip_video_frames;
|
||||
float avi_audio_pts;
|
||||
float avi_video_pts;
|
||||
float pts_correction;
|
||||
unsigned int pts_corr_bytes;
|
||||
unsigned char pts_corrected;
|
||||
unsigned char pts_has_video;
|
||||
} avi_priv_t;
|
||||
|
||||
#define AVI_PRIV ((avi_priv_t*)(demuxer->priv))
|
||||
|
13
aviprint.c
13
aviprint.c
@ -79,14 +79,23 @@ void print_video_header(BITMAPINFOHEADER *h){
|
||||
|
||||
void print_index(AVIINDEXENTRY *idx,int idx_size){
|
||||
int i;
|
||||
unsigned int pos[256];
|
||||
unsigned int num[256];
|
||||
for(i=0;i<256;i++) num[i]=pos[i]=0;
|
||||
for(i=0;i<idx_size;i++){
|
||||
printf("%5d: %.4s %4X %08X %ld\n",i,
|
||||
int id=avi_stream_id(idx[i].ckid);
|
||||
if(id<0 || id>255) id=255;
|
||||
printf("%5d: %.4s %4X %08X len:%6ld pos:%7d->%7.3f %7d->%7.3f\n",i,
|
||||
(char *)&idx[i].ckid,
|
||||
(unsigned int)idx[i].dwFlags,
|
||||
(unsigned int)idx[i].dwChunkOffset,
|
||||
// idx[i].dwChunkOffset+demuxer->movi_start,
|
||||
idx[i].dwChunkLength
|
||||
idx[i].dwChunkLength,
|
||||
pos[id],(float)pos[id]/18747.0f,
|
||||
num[id],(float)num[id]/23.976f
|
||||
);
|
||||
pos[id]+=idx[i].dwChunkLength;
|
||||
++num[id];
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -282,6 +282,7 @@ int decode_audio(sh_audio_t *sh_audio,unsigned char *buf,int minlen,int maxlen){
|
||||
switch(sh_audio->codec->driver){
|
||||
case AFM_MPEG: // MPEG layer 2 or 3
|
||||
len=MP3_DecodeFrame(buf,-1);
|
||||
// len=MP3_DecodeFrame(buf,3);
|
||||
break;
|
||||
case AFM_PCM: // AVI PCM
|
||||
len=demux_read_data(sh_audio->ds,buf,minlen);
|
||||
|
@ -37,13 +37,6 @@ extern int asf_packetsize;
|
||||
|
||||
// based on asf file-format doc by Eugene [http://divx.euro.ru]
|
||||
|
||||
//static float avi_pts_frametime=1.0f/25.0f;
|
||||
//static float avi_audio_pts=0;
|
||||
//static float avi_video_pts=0;
|
||||
|
||||
//static int skip_video_frames=0;
|
||||
|
||||
|
||||
static void asf_descrambling(unsigned char *src,int len){
|
||||
unsigned char *dst=malloc(len);
|
||||
unsigned char *s2=src;
|
||||
|
286
demux_avi.c
286
demux_avi.c
@ -1,4 +1,4 @@
|
||||
// AVI file parser for DEMUXER v2.6 by A'rpi/ESP-team
|
||||
// AVI file parser for DEMUXER v2.9 by A'rpi/ESP-team
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
@ -16,11 +16,7 @@ extern int verbose; // defined in mplayer.c
|
||||
#include "codec-cfg.h"
|
||||
#include "stheader.h"
|
||||
|
||||
//static float avi_pts_frametime=1.0f/25.0f;
|
||||
float avi_audio_pts=0;
|
||||
float avi_video_pts=0;
|
||||
//float avi_video_ftime=0.04;
|
||||
int skip_video_frames=0;
|
||||
#include "aviheader.h"
|
||||
|
||||
// Select ds from ID
|
||||
demux_stream_t* demux_avi_select_stream(demuxer_t *demux,unsigned int id){
|
||||
@ -58,12 +54,9 @@ demux_stream_t* demux_avi_select_stream(demuxer_t *demux,unsigned int id){
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static float pts_correction=0.0;
|
||||
static int pts_corrected=0;
|
||||
static int pts_has_video=0;
|
||||
static unsigned int pts_corr_bytes=0;
|
||||
|
||||
static int demux_avi_read_packet(demuxer_t *demux,unsigned int id,unsigned int len,int idxpos,int flags){
|
||||
avi_priv_t *priv=demux->priv;
|
||||
int skip;
|
||||
float pts=0;
|
||||
demux_stream_t *ds=demux_avi_select_stream(demux,id);
|
||||
@ -72,50 +65,50 @@ static int demux_avi_read_packet(demuxer_t *demux,unsigned int id,unsigned int l
|
||||
|
||||
if(ds==demux->audio){
|
||||
|
||||
if(pts_corrected==0){
|
||||
// printf("\rYYY-A A: %5.3f V: %5.3f \n",avi_audio_pts,avi_video_pts);
|
||||
if(pts_has_video){
|
||||
if(priv->pts_corrected==0){
|
||||
// printf("\rYYY-A A: %5.3f V: %5.3f \n",priv->avi_audio_pts,priv->avi_video_pts);
|
||||
if(priv->pts_has_video){
|
||||
// we have video pts now
|
||||
float delay=(float)pts_corr_bytes/((sh_audio_t*)(ds->sh))->wf->nAvgBytesPerSec;
|
||||
printf("XXX initial v_pts=%5.3f a_pos=%d (%5.3f) \n",avi_audio_pts,pts_corr_bytes,delay);
|
||||
//pts_correction=-avi_audio_pts+delay;
|
||||
pts_correction=delay-avi_audio_pts;
|
||||
avi_audio_pts+=pts_correction;
|
||||
pts_corrected=1;
|
||||
float delay=(float)priv->pts_corr_bytes/((sh_audio_t*)(ds->sh))->wf->nAvgBytesPerSec;
|
||||
printf("XXX initial v_pts=%5.3f a_pos=%d (%5.3f) \n",priv->avi_audio_pts,priv->pts_corr_bytes,delay);
|
||||
//priv->pts_correction=-priv->avi_audio_pts+delay;
|
||||
priv->pts_correction=delay-priv->avi_audio_pts;
|
||||
priv->avi_audio_pts+=priv->pts_correction;
|
||||
priv->pts_corrected=1;
|
||||
} else
|
||||
pts_corr_bytes+=len;
|
||||
priv->pts_corr_bytes+=len;
|
||||
}
|
||||
pts=avi_audio_pts; //+pts_correction;
|
||||
avi_audio_pts=0;
|
||||
pts=priv->avi_audio_pts; //+priv->pts_correction;
|
||||
priv->avi_audio_pts=0;
|
||||
} else
|
||||
if(ds==demux->video){
|
||||
// video
|
||||
if(skip_video_frames>0){
|
||||
if(priv->skip_video_frames>0){
|
||||
// drop frame (seeking)
|
||||
--skip_video_frames;
|
||||
--priv->skip_video_frames;
|
||||
ds=NULL;
|
||||
} else {
|
||||
pts=avi_video_pts;
|
||||
pts=priv->avi_video_pts;
|
||||
}
|
||||
// ezt a 2 sort lehet hogy fell kell majd cserelni:
|
||||
//avi_video_pts+=avi_pts_frametime;
|
||||
//avi_video_pts+=(float)avi_header.video.dwScale/(float)avi_header.video.dwRate;
|
||||
//avi_video_pts+=((sh_video_t*)ds->sh)->frametime;
|
||||
//priv->avi_video_pts+=avi_pts_frametime;
|
||||
//priv->avi_video_pts+=(float)avi_header.video.dwScale/(float)avi_header.video.dwRate;
|
||||
//priv->avi_video_pts+=((sh_video_t*)ds->sh)->frametime;
|
||||
// FIXME!!!
|
||||
#if 1
|
||||
// printf("ds=0x%X\n",ds);
|
||||
// printf("packno=%d\n",ds->pack_no);
|
||||
// printf("### pack_no=%d\n",demux->video->pack_no+demux->video->packs);
|
||||
avi_video_pts = (demux->video->pack_no+demux->video->packs) *
|
||||
priv->avi_video_pts = (demux->video->pack_no+demux->video->packs) *
|
||||
(float)((sh_video_t*)demux->video->sh)->video.dwScale /
|
||||
(float)((sh_video_t*)demux->video->sh)->video.dwRate;
|
||||
#else
|
||||
avi_video_pts+=(float)((sh_video_t*)(demux->video->sh))->video.dwScale/(float)((sh_video_t*)(demux->video->sh))->video.dwRate;
|
||||
// avi_video_pts+=avi_video_ftime;
|
||||
priv->avi_video_pts+=(float)((sh_video_t*)(demux->video->sh))->video.dwScale/(float)((sh_video_t*)(demux->video->sh))->video.dwRate;
|
||||
// priv->avi_video_pts+=avi_video_ftime;
|
||||
#endif
|
||||
// printf("\rYYY-V A: %5.3f V: %5.3f \n",avi_audio_pts,avi_video_pts);
|
||||
avi_audio_pts=avi_video_pts+pts_correction;
|
||||
pts_has_video=1;
|
||||
// printf("\rYYY-V A: %5.3f V: %5.3f \n",priv->avi_audio_pts,priv->avi_video_pts);
|
||||
priv->avi_audio_pts=priv->avi_video_pts+priv->pts_correction;
|
||||
priv->pts_has_video=1;
|
||||
|
||||
}
|
||||
|
||||
@ -134,13 +127,11 @@ static int demux_avi_read_packet(demuxer_t *demux,unsigned int id,unsigned int l
|
||||
return ds?1:0;
|
||||
}
|
||||
|
||||
//static int num_elementary_packets100=0;
|
||||
//static int num_elementary_packets101=0;
|
||||
|
||||
// return value:
|
||||
// 0 = EOF or no stream found
|
||||
// 1 = successfully read a packet
|
||||
int demux_avi_fill_buffer(demuxer_t *demux){
|
||||
avi_priv_t *priv=demux->priv;
|
||||
unsigned int id=0;
|
||||
unsigned int len;
|
||||
int max_packs=128;
|
||||
@ -157,14 +148,14 @@ do{
|
||||
}
|
||||
if(stream_eof(demux->stream)) return 0;
|
||||
#endif
|
||||
if(demux->idx_size>0 && demux->idx_pos<demux->idx_size){
|
||||
if(priv->idx_size>0 && priv->idx_pos<priv->idx_size){
|
||||
unsigned int pos;
|
||||
|
||||
//if(demux->idx_pos<0) printf("Fatal! idx_pos=%d\n",demux->idx_pos);
|
||||
//if(priv->idx_pos<0) printf("Fatal! idx_pos=%d\n",priv->idx_pos);
|
||||
|
||||
idx=&((AVIINDEXENTRY *)demux->idx)[demux->idx_pos++];
|
||||
idx=&((AVIINDEXENTRY *)priv->idx)[priv->idx_pos++];
|
||||
|
||||
//printf("[%d]",demux->idx_pos);fflush(stdout);
|
||||
//printf("[%d]",priv->idx_pos);fflush(stdout);
|
||||
|
||||
//stream_seek(demux->stream,idx.dwChunkOffset);
|
||||
//printf("IDX pos=%X idx.pos=%X idx.size=%X idx.flags=%X\n",demux->filepos,
|
||||
@ -178,7 +169,7 @@ do{
|
||||
continue; // skip this chunk
|
||||
}
|
||||
|
||||
pos=idx->dwChunkOffset+demux->idx_offset;
|
||||
pos=idx->dwChunkOffset+priv->idx_offset;
|
||||
if(pos<demux->movi_start || pos>=demux->movi_end){
|
||||
printf("ChunkOffset out of range! idx=0x%X \n",pos);
|
||||
continue;
|
||||
@ -222,8 +213,8 @@ do{
|
||||
continue;
|
||||
}
|
||||
}
|
||||
ret=demux_avi_read_packet(demux,id,len,demux->idx_pos-1,flags);
|
||||
if(!ret && skip_video_frames<=0)
|
||||
ret=demux_avi_read_packet(demux,id,len,priv->idx_pos-1,flags);
|
||||
if(!ret && priv->skip_video_frames<=0)
|
||||
if(--max_packs==0){
|
||||
demux->stream->eof=1;
|
||||
printf("demux: file doesn't contain the selected audio or video stream\n");
|
||||
@ -238,6 +229,7 @@ do{
|
||||
// 0 = EOF or no stream found
|
||||
// 1 = successfully read a packet
|
||||
int demux_avi_fill_buffer_ni(demuxer_t *demux,demux_stream_t* ds){
|
||||
avi_priv_t *priv=demux->priv;
|
||||
unsigned int id=0;
|
||||
unsigned int len;
|
||||
int max_packs=128;
|
||||
@ -249,14 +241,14 @@ do{
|
||||
int idx_pos=0;
|
||||
demux->filepos=stream_tell(demux->stream);
|
||||
|
||||
if(ds==demux->video) idx_pos=demux->idx_pos_v++; else
|
||||
if(ds==demux->audio) idx_pos=demux->idx_pos_a++; else
|
||||
idx_pos=demux->idx_pos++;
|
||||
if(ds==demux->video) idx_pos=priv->idx_pos_v++; else
|
||||
if(ds==demux->audio) idx_pos=priv->idx_pos_a++; else
|
||||
idx_pos=priv->idx_pos++;
|
||||
|
||||
if(demux->idx_size>0 && idx_pos<demux->idx_size){
|
||||
if(priv->idx_size>0 && idx_pos<priv->idx_size){
|
||||
unsigned int pos;
|
||||
idx=&((AVIINDEXENTRY *)demux->idx)[idx_pos];
|
||||
// idx=&demux->idx[idx_pos];
|
||||
idx=&((AVIINDEXENTRY *)priv->idx)[idx_pos];
|
||||
// idx=&priv->idx[idx_pos];
|
||||
|
||||
if(idx->dwFlags&AVIIF_LIST){
|
||||
// LIST
|
||||
@ -267,7 +259,7 @@ do{
|
||||
continue; // skip this chunk
|
||||
}
|
||||
|
||||
pos=idx->dwChunkOffset+demux->idx_offset;
|
||||
pos=idx->dwChunkOffset+priv->idx_offset;
|
||||
if(pos<demux->movi_start || pos>=demux->movi_end){
|
||||
printf("ChunkOffset out of range! current=0x%X idx=0x%X \n",demux->filepos,pos);
|
||||
continue;
|
||||
@ -299,7 +291,7 @@ do{
|
||||
if(idx->dwFlags&AVIIF_KEYFRAME) flags=1;
|
||||
} else return 0;
|
||||
ret=demux_avi_read_packet(demux,id,len,idx_pos,flags);
|
||||
if(!ret && skip_video_frames<=0)
|
||||
if(!ret && priv->skip_video_frames<=0)
|
||||
if(--max_packs==0){
|
||||
demux->stream->eof=1;
|
||||
printf("demux: file doesn't contain the selected audio or video stream\n");
|
||||
@ -314,13 +306,14 @@ do{
|
||||
// 0 = EOF or no stream found
|
||||
// 1 = successfully read a packet
|
||||
int demux_avi_fill_buffer_nini(demuxer_t *demux,demux_stream_t* ds){
|
||||
avi_priv_t *priv=demux->priv;
|
||||
unsigned int id=0;
|
||||
unsigned int len;
|
||||
int ret=0;
|
||||
int *fpos=NULL;
|
||||
|
||||
if(ds==demux->video) fpos=&demux->idx_pos_v; else
|
||||
if(ds==demux->audio) fpos=&demux->idx_pos_a; else
|
||||
if(ds==demux->video) fpos=&priv->idx_pos_v; else
|
||||
if(ds==demux->audio) fpos=&priv->idx_pos_a; else
|
||||
return 0;
|
||||
|
||||
stream_seek(demux->stream,fpos[0]);
|
||||
@ -343,7 +336,7 @@ do{
|
||||
|
||||
if(ds==demux_avi_select_stream(demux,id)){
|
||||
// read it!
|
||||
ret=demux_avi_read_packet(demux,id,len,demux->idx_pos-1,0);
|
||||
ret=demux_avi_read_packet(demux,id,len,priv->idx_pos-1,0);
|
||||
} else {
|
||||
// skip it!
|
||||
int skip=(len+1)&(~1); // total bytes in this chunk
|
||||
@ -355,9 +348,130 @@ do{
|
||||
return 1;
|
||||
}
|
||||
|
||||
extern float initial_pts_delay;
|
||||
extern int audio_id;
|
||||
extern int video_id;
|
||||
extern int index_mode; // -1=untouched 0=don't use index 1=use (geneate) index
|
||||
extern int force_ni;
|
||||
extern int pts_from_bps;
|
||||
|
||||
demuxer_t* demux_open_avi(demuxer_t* demuxer){
|
||||
demux_stream_t *d_audio=demuxer->audio;
|
||||
demux_stream_t *d_video=demuxer->video;
|
||||
sh_audio_t *sh_audio=NULL;
|
||||
sh_video_t *sh_video=NULL;
|
||||
avi_priv_t* priv=malloc(sizeof(avi_priv_t));
|
||||
|
||||
// priv struct:
|
||||
priv->avi_audio_pts=priv->avi_video_pts=0.0f;
|
||||
priv->pts_correction=0.0f;
|
||||
priv->skip_video_frames=0;
|
||||
priv->pts_corr_bytes=0;
|
||||
priv->pts_has_video=priv->pts_corrected=0;
|
||||
demuxer->priv=(void*)priv;
|
||||
|
||||
//---- AVI header:
|
||||
read_avi_header(demuxer,(demuxer->stream->type!=STREAMTYPE_STREAM)?index_mode:-2);
|
||||
stream_reset(demuxer->stream);
|
||||
stream_seek(demuxer->stream,demuxer->movi_start);
|
||||
priv->idx_pos=0;
|
||||
priv->idx_pos_a=0;
|
||||
priv->idx_pos_v=0;
|
||||
if(priv->idx_size>0){
|
||||
// decide index format:
|
||||
if(((AVIINDEXENTRY *)priv->idx)[0].dwChunkOffset<demuxer->movi_start)
|
||||
priv->idx_offset=demuxer->movi_start-4;
|
||||
else
|
||||
priv->idx_offset=0;
|
||||
if(verbose) printf("AVI index offset: %d\n",priv->idx_offset);
|
||||
}
|
||||
// demuxer->endpos=avi_header.movi_end;
|
||||
|
||||
if(priv->idx_size>0){
|
||||
// check that file is non-interleaved:
|
||||
int i;
|
||||
int a_pos=-1;
|
||||
int v_pos=-1;
|
||||
for(i=0;i<priv->idx_size;i++){
|
||||
AVIINDEXENTRY* idx=&((AVIINDEXENTRY *)priv->idx)[i];
|
||||
demux_stream_t* ds=demux_avi_select_stream(demuxer,idx->ckid);
|
||||
int pos=idx->dwChunkOffset+priv->idx_offset;
|
||||
if(a_pos==-1 && ds==demuxer->audio){
|
||||
a_pos=pos;
|
||||
if(v_pos!=-1) break;
|
||||
}
|
||||
if(v_pos==-1 && ds==demuxer->video){
|
||||
v_pos=pos;
|
||||
if(a_pos!=-1) break;
|
||||
}
|
||||
}
|
||||
if(v_pos==-1){
|
||||
fprintf(stderr,"AVI_NI: missing video stream!? contact the author, it may be a bug :(\n");
|
||||
return NULL;
|
||||
// GUI_MSG( mplErrorAVINI )
|
||||
// exit(1);
|
||||
}
|
||||
if(a_pos==-1){
|
||||
printf("AVI_NI: No audio stream found -> nosound\n");
|
||||
sh_audio=NULL;
|
||||
} else {
|
||||
if(force_ni || abs(a_pos-v_pos)>0x100000){ // distance > 1MB
|
||||
printf("%s NON-INTERLEAVED AVI file-format!\n",force_ni?"Forced":"Detected");
|
||||
demuxer->type=DEMUXER_TYPE_AVI_NI; // HACK!!!!
|
||||
pts_from_bps=1; // force BPS sync!
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// no index
|
||||
if(force_ni){
|
||||
printf("Using NON-INTERLEAVED Broken AVI file-format!\n");
|
||||
demuxer->type=DEMUXER_TYPE_AVI_NINI; // HACK!!!!
|
||||
priv->idx_pos_a=
|
||||
priv->idx_pos_v=demuxer->movi_start;
|
||||
pts_from_bps=1; // force BPS sync!
|
||||
}
|
||||
}
|
||||
if(!ds_fill_buffer(d_video)){
|
||||
fprintf(stderr,"AVI: missing video stream!? contact the author, it may be a bug :(\n");
|
||||
return NULL;
|
||||
// GUI_MSG( mplAVIErrorMissingVideoStream )
|
||||
// exit(1);
|
||||
}
|
||||
sh_video=d_video->sh;sh_video->ds=d_video;
|
||||
if(audio_id!=-2){
|
||||
if(verbose) printf("AVI: Searching for audio stream (id:%d)\n",d_audio->id);
|
||||
if(!ds_fill_buffer(d_audio)){
|
||||
printf("AVI: No Audio stream found... ->nosound\n");
|
||||
sh_audio=NULL;
|
||||
} else {
|
||||
sh_audio=d_audio->sh;sh_audio->ds=d_audio;
|
||||
sh_audio->format=sh_audio->wf->wFormatTag;
|
||||
}
|
||||
}
|
||||
// calc. FPS:
|
||||
sh_video->fps=(float)sh_video->video.dwRate/(float)sh_video->video.dwScale;
|
||||
sh_video->frametime=(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
// calculating video bitrate:
|
||||
sh_video->i_bps=demuxer->movi_end-demuxer->movi_start-priv->idx_size*8;
|
||||
if(sh_audio) sh_video->i_bps-=sh_audio->audio.dwLength;
|
||||
if(verbose) printf("AVI video length=%d\n",sh_video->i_bps);
|
||||
sh_video->i_bps=((float)sh_video->i_bps/(float)sh_video->video.dwLength)*sh_video->fps;
|
||||
printf("VIDEO: [%.4s] %ldx%ld %dbpp %4.2f fps %5.1f kbps (%4.1f kbyte/s)\n",
|
||||
(char *)&sh_video->bih->biCompression,
|
||||
sh_video->bih->biWidth,
|
||||
sh_video->bih->biHeight,
|
||||
sh_video->bih->biBitCount,
|
||||
sh_video->fps,
|
||||
sh_video->i_bps*0.008f,
|
||||
sh_video->i_bps/1024.0f );
|
||||
|
||||
return demuxer;
|
||||
|
||||
}
|
||||
|
||||
//extern float initial_pts_delay;
|
||||
|
||||
void demux_seek_avi(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
avi_priv_t *priv=demuxer->priv;
|
||||
demux_stream_t *d_audio=demuxer->audio;
|
||||
demux_stream_t *d_video=demuxer->video;
|
||||
sh_audio_t *sh_audio=d_audio->sh;
|
||||
@ -370,40 +484,40 @@ void demux_seek_avi(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
int video_chunk_pos=d_video->pos;
|
||||
int i;
|
||||
|
||||
skip_video_frames=0;
|
||||
avi_audio_pts=0;
|
||||
priv->skip_video_frames=0;
|
||||
priv->avi_audio_pts=0;
|
||||
|
||||
// ------------ STEP 1: find nearest video keyframe chunk ------------
|
||||
// find nearest video keyframe chunk pos:
|
||||
if(rel_seek_frames>0){
|
||||
// seek forward
|
||||
while(video_chunk_pos<demuxer->idx_size){
|
||||
int id=((AVIINDEXENTRY *)demuxer->idx)[video_chunk_pos].ckid;
|
||||
while(video_chunk_pos<priv->idx_size){
|
||||
int id=((AVIINDEXENTRY *)priv->idx)[video_chunk_pos].ckid;
|
||||
if(avi_stream_id(id)==d_video->id){ // video frame
|
||||
if((--rel_seek_frames)<0 && ((AVIINDEXENTRY *)demuxer->idx)[video_chunk_pos].dwFlags&AVIIF_KEYFRAME) break;
|
||||
if((--rel_seek_frames)<0 && ((AVIINDEXENTRY *)priv->idx)[video_chunk_pos].dwFlags&AVIIF_KEYFRAME) break;
|
||||
}
|
||||
++video_chunk_pos;
|
||||
}
|
||||
} else {
|
||||
// seek backward
|
||||
while(video_chunk_pos>=0){
|
||||
int id=((AVIINDEXENTRY *)demuxer->idx)[video_chunk_pos].ckid;
|
||||
int id=((AVIINDEXENTRY *)priv->idx)[video_chunk_pos].ckid;
|
||||
if(avi_stream_id(id)==d_video->id){ // video frame
|
||||
if((++rel_seek_frames)>0 && ((AVIINDEXENTRY *)demuxer->idx)[video_chunk_pos].dwFlags&AVIIF_KEYFRAME) break;
|
||||
if((++rel_seek_frames)>0 && ((AVIINDEXENTRY *)priv->idx)[video_chunk_pos].dwFlags&AVIIF_KEYFRAME) break;
|
||||
}
|
||||
--video_chunk_pos;
|
||||
}
|
||||
}
|
||||
demuxer->idx_pos_a=demuxer->idx_pos_v=demuxer->idx_pos=video_chunk_pos;
|
||||
priv->idx_pos_a=priv->idx_pos_v=priv->idx_pos=video_chunk_pos;
|
||||
|
||||
// re-calc video pts:
|
||||
d_video->pack_no=0;
|
||||
for(i=0;i<video_chunk_pos;i++){
|
||||
int id=((AVIINDEXENTRY *)demuxer->idx)[i].ckid;
|
||||
int id=((AVIINDEXENTRY *)priv->idx)[i].ckid;
|
||||
if(avi_stream_id(id)==d_video->id) ++d_video->pack_no;
|
||||
}
|
||||
sh_video->num_frames=d_video->pack_no;
|
||||
avi_video_pts=d_video->pack_no*(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
priv->avi_video_pts=d_video->pack_no*(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
d_video->pos=video_chunk_pos;
|
||||
|
||||
// ------------ STEP 2: seek audio, find the right chunk & pos ------------
|
||||
@ -419,28 +533,28 @@ void demux_seek_avi(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
int skip_audio_bytes=0;
|
||||
int curr_audio_pos=-1;
|
||||
int audio_chunk_pos=-1;
|
||||
int chunk_max=(demuxer->type==DEMUXER_TYPE_AVI)?video_chunk_pos:demuxer->idx_size;
|
||||
int chunk_max=(demuxer->type==DEMUXER_TYPE_AVI)?video_chunk_pos:priv->idx_size;
|
||||
|
||||
if(sh_audio->audio.dwSampleSize){
|
||||
// constant rate audio stream
|
||||
#if 0
|
||||
int align;
|
||||
curr_audio_pos=(avi_video_pts) * sh_audio->wf->nAvgBytesPerSec;
|
||||
curr_audio_pos=(priv->avi_video_pts) * sh_audio->wf->nAvgBytesPerSec;
|
||||
if(curr_audio_pos<0)curr_audio_pos=0;
|
||||
align=sh_audio->audio.dwSampleSize;
|
||||
if(sh_audio->wf->nBlockAlign>align) align=sh_audio->wf->nBlockAlign;
|
||||
curr_audio_pos/=align;
|
||||
curr_audio_pos*=align;
|
||||
#else
|
||||
curr_audio_pos=(avi_video_pts)*(float)sh_audio->audio.dwRate/(float)sh_audio->audio.dwScale;
|
||||
curr_audio_pos=(priv->avi_video_pts)*(float)sh_audio->audio.dwRate/(float)sh_audio->audio.dwScale;
|
||||
curr_audio_pos*=sh_audio->audio.dwSampleSize;
|
||||
#endif
|
||||
|
||||
// find audio chunk pos:
|
||||
for(i=0;i<chunk_max;i++){
|
||||
int id=((AVIINDEXENTRY *)demuxer->idx)[i].ckid;
|
||||
int id=((AVIINDEXENTRY *)priv->idx)[i].ckid;
|
||||
if(avi_stream_id(id)==d_audio->id){
|
||||
len=((AVIINDEXENTRY *)demuxer->idx)[i].dwChunkLength;
|
||||
len=((AVIINDEXENTRY *)priv->idx)[i].dwChunkLength;
|
||||
audio_chunk_pos=i; ++d_audio->pack_no;
|
||||
if(d_audio->dpos<=curr_audio_pos && curr_audio_pos<(d_audio->dpos+len)){
|
||||
//if(verbose)printf("break;\n");
|
||||
@ -453,14 +567,14 @@ void demux_seek_avi(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
|
||||
} else {
|
||||
// VBR audio
|
||||
int chunks=(avi_video_pts)*(float)sh_audio->audio.dwRate/(float)sh_audio->audio.dwScale;
|
||||
int chunks=(priv->avi_video_pts)*(float)sh_audio->audio.dwRate/(float)sh_audio->audio.dwScale;
|
||||
audio_chunk_pos=0;
|
||||
|
||||
// find audio chunk pos:
|
||||
for(i=0;i<demuxer->idx_size && chunks>0;i++){
|
||||
int id=((AVIINDEXENTRY *)demuxer->idx)[i].ckid;
|
||||
for(i=0;i<priv->idx_size && chunks>0;i++){
|
||||
int id=((AVIINDEXENTRY *)priv->idx)[i].ckid;
|
||||
if(avi_stream_id(id)==d_audio->id){
|
||||
len=((AVIINDEXENTRY *)demuxer->idx)[i].dwChunkLength;
|
||||
len=((AVIINDEXENTRY *)priv->idx)[i].dwChunkLength;
|
||||
if(i>chunk_max){
|
||||
skip_audio_bytes+=len;
|
||||
} else {
|
||||
@ -474,7 +588,7 @@ void demux_seek_avi(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
//if(audio_chunk_pos>chunk_max) audio_chunk_pos=chunk_max;
|
||||
|
||||
// printf("VBR seek: %5.3f -> chunk_no %d -> chunk_idx %d + skip %d \n",
|
||||
// avi_video_pts, audio_chunk_pos, );
|
||||
// priv->avi_video_pts, audio_chunk_pos, );
|
||||
|
||||
}
|
||||
|
||||
@ -493,25 +607,25 @@ void demux_seek_avi(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
if(demuxer->type==DEMUXER_TYPE_AVI){
|
||||
// interleaved stream:
|
||||
if(audio_chunk_pos<video_chunk_pos){
|
||||
// calc skip_video_frames & adjust video pts counter:
|
||||
// calc priv->skip_video_frames & adjust video pts counter:
|
||||
for(i=audio_chunk_pos;i<video_chunk_pos;i++){
|
||||
int id=((AVIINDEXENTRY *)demuxer->idx)[i].ckid;
|
||||
if(avi_stream_id(id)==d_video->id) ++skip_video_frames;
|
||||
int id=((AVIINDEXENTRY *)priv->idx)[i].ckid;
|
||||
if(avi_stream_id(id)==d_video->id) ++priv->skip_video_frames;
|
||||
}
|
||||
// requires for correct audio pts calculation (demuxer):
|
||||
avi_video_pts-=skip_video_frames*(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
demuxer->idx_pos_a=demuxer->idx_pos_v=demuxer->idx_pos=audio_chunk_pos;
|
||||
priv->avi_video_pts-=priv->skip_video_frames*(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
priv->idx_pos_a=priv->idx_pos_v=priv->idx_pos=audio_chunk_pos;
|
||||
}
|
||||
} else {
|
||||
// non-interleaved stream:
|
||||
demuxer->idx_pos_a=audio_chunk_pos;
|
||||
demuxer->idx_pos_v=video_chunk_pos;
|
||||
demuxer->idx_pos=(audio_chunk_pos<video_chunk_pos)?audio_chunk_pos:video_chunk_pos;
|
||||
priv->idx_pos_a=audio_chunk_pos;
|
||||
priv->idx_pos_v=video_chunk_pos;
|
||||
priv->idx_pos=(audio_chunk_pos<video_chunk_pos)?audio_chunk_pos:video_chunk_pos;
|
||||
}
|
||||
|
||||
if(verbose) printf("SEEK: idx=%d (a:%d v:%d) v.skip=%d a.skip=%d/%4.3f \n",
|
||||
demuxer->idx_pos,audio_chunk_pos,video_chunk_pos,
|
||||
skip_video_frames,skip_audio_bytes,skip_audio_secs);
|
||||
priv->idx_pos,audio_chunk_pos,video_chunk_pos,
|
||||
priv->skip_video_frames,skip_audio_bytes,skip_audio_secs);
|
||||
|
||||
if(skip_audio_bytes){
|
||||
demux_read_data(d_audio,NULL,skip_audio_bytes);
|
||||
|
105
demuxer.c
105
demuxer.c
@ -294,7 +294,6 @@ extern int num_elementary_packetsPES;
|
||||
|
||||
// commandline options, flags:
|
||||
extern int seek_to_byte;
|
||||
extern int index_mode; // -1=untouched 0=don't use index 1=use (geneate) index
|
||||
extern int force_ni;
|
||||
extern int pts_from_bps;
|
||||
|
||||
@ -391,8 +390,8 @@ if(file_format==DEMUXER_TYPE_MPEG_ES){ // little hack, see above!
|
||||
printf("Detected MPEG-ES file format!\n");
|
||||
}
|
||||
}
|
||||
#ifdef MOV
|
||||
//=============== Try to open as MOV file: =================
|
||||
#if 0
|
||||
if(file_format==DEMUXER_TYPE_UNKNOWN || file_format==DEMUXER_TYPE_MOV){
|
||||
stream_reset(stream);
|
||||
demuxer=new_demuxer(stream,DEMUXER_TYPE_MOV,audio_id,video_id,dvdsub_id);
|
||||
@ -416,110 +415,19 @@ d_audio=demuxer->audio;
|
||||
d_video=demuxer->video;
|
||||
//d_dvdsub=demuxer->sub;
|
||||
|
||||
demuxer->file_format=file_format;
|
||||
|
||||
switch(file_format){
|
||||
case DEMUXER_TYPE_AVI: {
|
||||
//---- AVI header:
|
||||
read_avi_header(demuxer,(stream->type!=STREAMTYPE_STREAM)?index_mode:-2);
|
||||
stream_reset(demuxer->stream);
|
||||
stream_seek(demuxer->stream,demuxer->movi_start);
|
||||
demuxer->idx_pos=0;
|
||||
demuxer->idx_pos_a=0;
|
||||
demuxer->idx_pos_v=0;
|
||||
if(demuxer->idx_size>0){
|
||||
// decide index format:
|
||||
if(((AVIINDEXENTRY *)demuxer->idx)[0].dwChunkOffset<demuxer->movi_start)
|
||||
demuxer->idx_offset=demuxer->movi_start-4;
|
||||
else
|
||||
demuxer->idx_offset=0;
|
||||
if(verbose) printf("AVI index offset: %d\n",demuxer->idx_offset);
|
||||
}
|
||||
// demuxer->endpos=avi_header.movi_end;
|
||||
|
||||
if(demuxer->idx_size>0){
|
||||
// check that file is non-interleaved:
|
||||
int i;
|
||||
int a_pos=-1;
|
||||
int v_pos=-1;
|
||||
for(i=0;i<demuxer->idx_size;i++){
|
||||
AVIINDEXENTRY* idx=&((AVIINDEXENTRY *)demuxer->idx)[i];
|
||||
demux_stream_t* ds=demux_avi_select_stream(demuxer,idx->ckid);
|
||||
int pos=idx->dwChunkOffset+demuxer->idx_offset;
|
||||
if(a_pos==-1 && ds==demuxer->audio){
|
||||
a_pos=pos;
|
||||
if(v_pos!=-1) break;
|
||||
}
|
||||
if(v_pos==-1 && ds==demuxer->video){
|
||||
v_pos=pos;
|
||||
if(a_pos!=-1) break;
|
||||
}
|
||||
}
|
||||
if(v_pos==-1){
|
||||
fprintf(stderr,"AVI_NI: missing video stream!? contact the author, it may be a bug :(\n");
|
||||
return NULL;
|
||||
// GUI_MSG( mplErrorAVINI )
|
||||
// exit(1);
|
||||
}
|
||||
if(a_pos==-1){
|
||||
printf("AVI_NI: No audio stream found -> nosound\n");
|
||||
sh_audio=NULL;
|
||||
} else {
|
||||
if(force_ni || abs(a_pos-v_pos)>0x100000){ // distance > 1MB
|
||||
printf("%s NON-INTERLEAVED AVI file-format!\n",force_ni?"Forced":"Detected");
|
||||
demuxer->type=DEMUXER_TYPE_AVI_NI; // HACK!!!!
|
||||
pts_from_bps=1; // force BPS sync!
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// no index
|
||||
if(force_ni){
|
||||
printf("Using NON-INTERLEAVED Broken AVI file-format!\n");
|
||||
demuxer->type=DEMUXER_TYPE_AVI_NINI; // HACK!!!!
|
||||
demuxer->idx_pos_a=
|
||||
demuxer->idx_pos_v=demuxer->movi_start;
|
||||
pts_from_bps=1; // force BPS sync!
|
||||
}
|
||||
}
|
||||
if(!ds_fill_buffer(d_video)){
|
||||
fprintf(stderr,"AVI: missing video stream!? contact the author, it may be a bug :(\n");
|
||||
return NULL;
|
||||
// GUI_MSG( mplAVIErrorMissingVideoStream )
|
||||
// exit(1);
|
||||
}
|
||||
sh_video=d_video->sh;sh_video->ds=d_video;
|
||||
if(audio_id!=-2){
|
||||
if(verbose) printf("AVI: Searching for audio stream (id:%d)\n",d_audio->id);
|
||||
if(!ds_fill_buffer(d_audio)){
|
||||
printf("AVI: No Audio stream found... ->nosound\n");
|
||||
sh_audio=NULL;
|
||||
} else {
|
||||
sh_audio=d_audio->sh;sh_audio->ds=d_audio;
|
||||
sh_audio->format=sh_audio->wf->wFormatTag;
|
||||
}
|
||||
}
|
||||
// calc. FPS:
|
||||
sh_video->fps=(float)sh_video->video.dwRate/(float)sh_video->video.dwScale;
|
||||
sh_video->frametime=(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
// calculating video bitrate:
|
||||
sh_video->i_bps=demuxer->movi_end-demuxer->movi_start-demuxer->idx_size*8;
|
||||
if(sh_audio) sh_video->i_bps-=sh_audio->audio.dwLength;
|
||||
if(verbose) printf("AVI video length=%d\n",sh_video->i_bps);
|
||||
sh_video->i_bps=((float)sh_video->i_bps/(float)sh_video->video.dwLength)*sh_video->fps;
|
||||
printf("VIDEO: [%.4s] %ldx%ld %dbpp %4.2f fps %5.1f kbps (%4.1f kbyte/s)\n",
|
||||
(char *)&sh_video->bih->biCompression,
|
||||
sh_video->bih->biWidth,
|
||||
sh_video->bih->biHeight,
|
||||
sh_video->bih->biBitCount,
|
||||
sh_video->fps,
|
||||
sh_video->i_bps*0.008f,
|
||||
sh_video->i_bps/1024.0f );
|
||||
break;
|
||||
return demux_open_avi(demuxer);
|
||||
// break;
|
||||
}
|
||||
case DEMUXER_TYPE_ASF: {
|
||||
//---- ASF header:
|
||||
read_asf_header(demuxer);
|
||||
stream_reset(demuxer->stream);
|
||||
stream_seek(demuxer->stream,demuxer->movi_start);
|
||||
demuxer->idx_pos=0;
|
||||
// demuxer->idx_pos=0;
|
||||
// demuxer->endpos=avi_header.movi_end;
|
||||
if(!ds_fill_buffer(d_video)){
|
||||
printf("ASF: no video stream found!\n");
|
||||
@ -575,6 +483,5 @@ switch(file_format){
|
||||
}
|
||||
} // switch(file_format)
|
||||
|
||||
demuxer->file_format=file_format;
|
||||
return demuxer;
|
||||
}
|
||||
|
29
demuxer.h
29
demuxer.h
@ -22,7 +22,7 @@
|
||||
typedef struct demux_packet_st {
|
||||
int len;
|
||||
float pts;
|
||||
off_t pos; // pozicio indexben (AVI) ill. fileban (MPG)
|
||||
off_t pos; // position in index (AVI) or file (MPG)
|
||||
unsigned char* buffer;
|
||||
int flags; // keyframe, etc
|
||||
struct demux_packet_st* next;
|
||||
@ -59,30 +59,19 @@ typedef struct demuxer_st {
|
||||
off_t filepos; // input stream current pos.
|
||||
int type; // demuxer type: mpeg PS, mpeg ES, avi, avi-ni, avi-nini, asf
|
||||
int file_format; // file format: mpeg/avi/asf
|
||||
// int time_src;// time source (pts/file/bps)
|
||||
off_t movi_start;
|
||||
off_t movi_end;
|
||||
//
|
||||
demux_stream_t *audio;
|
||||
demux_stream_t *video;
|
||||
demux_stream_t *sub;
|
||||
|
||||
// index:
|
||||
// AVIINDEXENTRY* idx;
|
||||
// FIXME: off_t???
|
||||
void* idx;
|
||||
int idx_size;
|
||||
int idx_pos;
|
||||
int idx_pos_a;
|
||||
int idx_pos_v;
|
||||
int idx_offset; // ennyit kell hozzaadni az index offset ertekekhez
|
||||
demux_stream_t *audio; // audio buffer/demuxer
|
||||
demux_stream_t *video; // video buffer/demuxer
|
||||
demux_stream_t *sub; // dvd subtitle buffer/demuxer
|
||||
|
||||
// stream headers:
|
||||
// sh_audio_t* a_streams[256];
|
||||
// sh_video_t* v_streams[256];
|
||||
void* a_streams[256];
|
||||
void* v_streams[256];
|
||||
char s_streams[32]; // dvd subtitles
|
||||
void* a_streams[256]; // audio streams (sh_audio_t)
|
||||
void* v_streams[256]; // video sterams (sh_video_t)
|
||||
char s_streams[32]; // dvd subtitles (flag)
|
||||
|
||||
void* priv; // fileformat-dependent data
|
||||
} demuxer_t;
|
||||
|
||||
inline static demux_packet_t* new_demux_packet(int len){
|
||||
|
@ -150,11 +150,6 @@ int encode_bitrate=0;
|
||||
|
||||
extern int asf_packetsize; // for seeking
|
||||
|
||||
extern float avi_audio_pts;
|
||||
extern float avi_video_pts;
|
||||
extern float avi_video_ftime;
|
||||
extern int skip_video_frames;
|
||||
|
||||
void read_avi_header(demuxer_t *demuxer,int index_mode);
|
||||
demux_stream_t* demux_avi_select_stream(demuxer_t *demux,unsigned int id);
|
||||
|
||||
@ -1362,7 +1357,7 @@ if(1)
|
||||
else // VBR:
|
||||
a_pts=d_audio->pack_no*(float)sh_audio->audio.dwScale/(float)sh_audio->audio.dwRate;
|
||||
v_pts=d_video->pack_no*(float)sh_video->video.dwScale/(float)sh_video->video.dwRate;
|
||||
if(verbose)printf("%5.3f|",v_pts-d_video->pts);
|
||||
// if(verbose)printf("%5.3f|",v_pts-d_video->pts);
|
||||
} else {
|
||||
if(!delay_corrected && d_audio->pts){
|
||||
// float x=d_audio->pts-d_video->pts-(delay);
|
||||
|
13
seek.c
13
seek.c
@ -22,11 +22,6 @@
|
||||
|
||||
//extern int asf_packetsize; // for seeking
|
||||
|
||||
//extern float avi_audio_pts;
|
||||
//extern float avi_video_pts;
|
||||
//extern float avi_video_ftime;
|
||||
//extern int skip_video_frames;
|
||||
//extern int seek_to_byte;
|
||||
//extern char* current_module; // for debugging
|
||||
|
||||
// flags:
|
||||
@ -44,10 +39,10 @@ int demux_seek(demuxer_t *demuxer,float rel_seek_secs,int flags){
|
||||
sh_video_t *sh_video=d_video->sh;
|
||||
// float skip_audio_secs=0;
|
||||
|
||||
if(demuxer->file_format==DEMUXER_TYPE_AVI && demuxer->idx_size<=0){
|
||||
printf("Can't seek in raw .AVI streams! (index required, try with the -idx switch!) \n");
|
||||
return 0;
|
||||
}
|
||||
//if(demuxer->file_format==DEMUXER_TYPE_AVI && demuxer->idx_size<=0){
|
||||
// printf("Can't seek in raw .AVI streams! (index required, try with the -idx switch!) \n");
|
||||
// return 0;
|
||||
//}
|
||||
|
||||
// current_module="seek";
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user