diff options
-rw-r--r-- | DOCS/codecs.conf | 40 | ||||
-rw-r--r-- | dll_init.c | 17 | ||||
-rw-r--r-- | loader/dshow/DS_Filter.c | 198 | ||||
-rw-r--r-- | loader/dshow/DS_Filter.h | 13 | ||||
-rw-r--r-- | loader/dshow/DS_VideoDec.c | 23 | ||||
-rw-r--r-- | loader/dshow/allocator.c | 13 | ||||
-rw-r--r-- | loader/dshow/allocator.h | 18 | ||||
-rw-r--r-- | loader/dshow/cmediasample.c | 3 | ||||
-rw-r--r-- | loader/dshow/cmediasample.h | 3 | ||||
-rw-r--r-- | loader/dshow/guids.c | 3 | ||||
-rw-r--r-- | loader/dshow/interfaces.h | 1 | ||||
-rw-r--r-- | loader/dshow/outputpin.c | 37 | ||||
-rw-r--r-- | loader/dshow/outputpin.h | 6 | ||||
-rw-r--r-- | loader/stubs.s | 4 | ||||
-rw-r--r-- | loader/win32.c | 108 |
15 files changed, 329 insertions, 158 deletions
diff --git a/DOCS/codecs.conf b/DOCS/codecs.conf index 3d8a91ac27..cdd5adaa51 100644 --- a/DOCS/codecs.conf +++ b/DOCS/codecs.conf @@ -9,6 +9,7 @@ videocodec mpeg12 comment "with postprocessing" status working format 0x1 + format 0xFFFFFF01 driver libmpeg2 dll "libmpeg2" out YV12 @@ -151,7 +152,7 @@ videocodec mjpeg out UYVY out BGR32,BGR24,BGR15 -videocodec wmv1 +videocodec wmv7 info "Windows Media Video 7" status working fourcc WMV1 @@ -162,6 +163,17 @@ videocodec wmv1 out YUY2 out BGR32,BGR24,BGR16,BGR15 +videocodec wmv8 + info "Windows Media Video 8" + status crashing + comment "Floating point exception" + fourcc WMV2 + driver dshow + dll "wmv8ds32.ax" + guid 0x521fb373, 0x7654, 0x49f2, 0xbd, 0xb1, 0x0c, 0x6e, 0x66, 0x60, 0x71, 0x4f + out YUY2 + out BGR32,BGR24,BGR16,BGR15 + videocodec ap41 info "AngelPotion Definitive V1" ; yet another stolen stuff comment "using the DivX ;-) codec" @@ -176,7 +188,7 @@ videocodec ap41 videocodec tm20 info "TrueMotion 2.0" status crashing - comment "Error connecting to output pin" + comment "segfault in the DLL" fourcc TM20 driver dshow dll "tm20dec.ax" @@ -248,15 +260,6 @@ videocodec mwv1 out YUY2 out BGR32,BGR24,BGR15 -videocodec wmv8 - info "Windows Media Video 8" - status untested - fourcc WMV2 - driver dshow - dll "wmv8ds32.ax" - guid 0x521fb373, 0x7654, 0x49f2, 0xbd, 0xb1, 0x0c, 0x6e, 0x66, 0x60, 0x71, 0x4f -; out YUY2 - out BGR32,BGR24,BGR16,BGR15 videocodec m261 info "M261" @@ -274,7 +277,18 @@ videocodec asv2 driver vfw dll "asusasv2.dll" ; out YVYU - out UYVY flip + out UYVY + out BGR32,BGR24,BGR15 flip + +videocodec asv1 + info "ASUS V1" + status buggy + comment "rgb upside down, yuv ok" + fourcc ASV1 + driver vfw + dll "asusasvd.dll" +; out YVYU + out UYVY out BGR32,BGR24,BGR15 flip ;============================================================================= @@ -300,7 +314,7 @@ audiocodec msadpcm audiocodec mp3acm info "MPEG layer-3" status working - comment "Optimized to Intel MMX/SSE" + comment "Optimized to Intel MMX/SSE, conflicts with security kernel patches" format 0x55 driver acm dll "l3codeca.acm" diff --git a/dll_init.c b/dll_init.c index ad0b6298c5..e65542d41c 100644 --- a/dll_init.c +++ b/dll_init.c @@ -166,6 +166,12 @@ int init_video_codec(sh_video_t *sh_video){ // sh_video->o_bih.biPlanes=3; // sh_video->o_bih.biBitCount=16; +#if 0 + // workaround for pegasus MJPEG: + if(!sh_video->o_bih.biWidth) sh_video->o_bih.biWidth=sh_video->bih->biWidth; + if(!sh_video->o_bih.biHeight) sh_video->o_bih.biHeight=sh_video->bih->biHeight; + if(!sh_video->o_bih.biPlanes) sh_video->o_bih.biPlanes=sh_video->bih->biPlanes; +#endif switch (outfmt) { @@ -213,7 +219,15 @@ int init_video_codec(sh_video_t *sh_video){ return 0; } + printf("XXX w=%d h=%d b=%d\n", + sh_video->o_bih.biWidth, + sh_video->o_bih.biHeight, + sh_video->o_bih.biBitCount/8 + ); + sh_video->o_bih.biSizeImage = sh_video->o_bih.biWidth * sh_video->o_bih.biHeight * (sh_video->o_bih.biBitCount/8); + + printf("XXX size=%d\n",sh_video->o_bih.biSizeImage); if(!(sh_video->codec->outflags[sh_video->outfmtidx]&CODECS_FLAG_FLIP)) { sh_video->o_bih.biHeight=-sh_video->bih->biHeight; // flip image! @@ -248,6 +262,7 @@ int init_video_codec(sh_video_t *sh_video){ } if(verbose) printf("ICDecompressQuery OK\n"); + printf("XXX size=%d\n",sh_video->o_bih.biSizeImage); ret = ICDecompressBegin(sh_video->hic, sh_video->bih, &sh_video->o_bih); if(ret){ @@ -255,6 +270,8 @@ int init_video_codec(sh_video_t *sh_video){ return 0; } + printf("XXX size=%d\n",sh_video->o_bih.biSizeImage); + #if 0 //sh_video->hic diff --git a/loader/dshow/DS_Filter.c b/loader/dshow/DS_Filter.c index 7d06473f9c..966b2cde87 100644 --- a/loader/dshow/DS_Filter.c +++ b/loader/dshow/DS_Filter.c @@ -4,6 +4,7 @@ #include <except.h> //#include "../loader/loader.h" #include <string> +#include <iostream> #define __MODULE__ "DirectShow generic filter" using namespace std; @@ -12,7 +13,6 @@ typedef long STDCALL (*GETCLASS) (const GUID*, const GUID*, void**); extern "C" char* def_path; extern "C" int STDCALL expLoadLibraryA(const char*); -//extern "C" int WINAPI expLoadLibraryA(char* name); extern "C" STDCALL void* GetProcAddress(int, const char*); extern "C" int STDCALL FreeLibrary(int); @@ -21,13 +21,51 @@ extern "C" void setup_FS_Segment(); DS_Filter::DS_Filter() :m_iHandle(0), m_pFilter(0), m_pInputPin(0), - m_pOutputPin(0), m_pSrcFilter(0), - m_pOurInput(0), m_pOurOutput(0), - m_pImp(0), m_pAll(0), m_pParentFilter(0) + m_pOutputPin(0), m_pSrcFilter(0), m_pParentFilter(0), + m_pOurInput(0), m_pOurOutput(0), m_pAll(0), m_pImp(0), + m_iState(0) { } -void DS_Filter::Create(char* dllname, const GUID* id, AM_MEDIA_TYPE* in_fmt, AM_MEDIA_TYPE* out_fmt) +void DS_Filter::clean() +{ + m_iState = 0; + + if (m_pOurInput) + m_pOurInput->vt->Release((IUnknown*)m_pOurInput); + if (m_pInputPin) + m_pInputPin->vt->Disconnect(m_pInputPin); + if (m_pOutputPin) + m_pOutputPin->vt->Disconnect(m_pOutputPin); + if (m_pFilter) + m_pFilter->vt->Release((IUnknown*)m_pFilter); + if (m_pOutputPin) + m_pOutputPin->vt->Release((IUnknown*)m_pOutputPin); + if (m_pInputPin) + m_pInputPin->vt->Release((IUnknown*)m_pInputPin); + if (m_pImp) + m_pImp->vt->Release((IUnknown*)m_pImp); + + delete m_pOurOutput; + delete m_pParentFilter; + delete m_pSrcFilter; + + // FIXME - we are still leaving few things allocated! + if (m_iHandle) + FreeLibrary(m_iHandle); + +} + +DS_Filter::~DS_Filter() +{ + //cout << "Destruction of DS_FILTER" << endl; + Stop(); + if (m_iState == 1) + clean(); + //cout << "Destruction of DS_FILTER done" << endl; +} + +void DS_Filter::Create(char* dllname, const GUID* id, AM_MEDIA_TYPE* in_fmt, AM_MEDIA_TYPE* out_fmt) { Setup_LDT_Keeper(); @@ -37,40 +75,37 @@ void DS_Filter::Create(char* dllname, const GUID* id, AM_MEDIA_TYPE* in_fmt, AM_ // string _fullname=def_path; // _fullname+="/"; // _fullname+=dllname; -// m_iHandle= LoadLibraryA(_fullname.c_str()); m_iHandle= expLoadLibraryA(dllname); - if(!m_iHandle)throw FATAL("Could not open DLL"); + if (!m_iHandle) + { + char e[1024]; + sprintf(e, "Could not open DirectShow DLL: %s", dllname); + throw FATAL(e); + } GETCLASS func=(GETCLASS)GetProcAddress(m_iHandle, "DllGetClassObject"); - if(!func)throw FATAL("Illegal or corrupt DLL"); + if (!func) + { + char e[1024]; + sprintf(e, "Illegal or corrupt DirectShow DLL: %s", dllname); + throw FATAL(e); + } HRESULT result; IClassFactory* factory=0; - IUnknown* object=0; - result=func(id, &IID_IClassFactory, (void**)&factory); if(result || (!factory)) throw FATAL("No such class object");; - -// printf("# factory = %X\n",(unsigned int)factory); -// printf("# factory->vt = %X\n",(unsigned int)factory->vt); -// printf("# factory->vt->CreateInstance = %X\n",(unsigned int)factory->vt->CreateInstance); - - setup_FS_Segment(); -// printf("Calling factory->vt->CreateInstance()\n"); - result=factory->vt->CreateInstance(factory, 0, &IID_IUnknown, (void**)&object); -// printf("Calling factory->vt->Release()\n"); - -// result=factory->vt->CreateInstance(factory, 0, &IID_IUnknown, (void**)&object); - -// printf("CreateInstance ok %x\n",result); + setup_FS_Segment(); + IUnknown* object=0; + result=factory->vt->CreateInstance(factory, 0, &IID_IUnknown, (void**)&object); factory->vt->Release((IUnknown*)factory); if(result || (!object)) throw FATAL("Class factory failure"); - + result=object->vt->QueryInterface(object, &IID_IBaseFilter, (void**)&m_pFilter); object->vt->Release((IUnknown*)object); if(result || (!m_pFilter)) throw FATAL("Object does not have IBaseFilter interface"); - + IEnumPins* enum_pins=0; // enumerate pins result=m_pFilter->vt->EnumPins(m_pFilter, &enum_pins); @@ -79,109 +114,96 @@ void DS_Filter::Create(char* dllname, const GUID* id, AM_MEDIA_TYPE* in_fmt, AM_ ULONG fetched; enum_pins->vt->Reset(enum_pins); result=enum_pins->vt->Next(enum_pins, (ULONG)256, (IPin**)array, &fetched); -// printf("Pins enumeration returned %d pins, error is %x\n", fetched, result); - - for(int i=0; i<fetched; i++) + Debug printf("Pins enumeration returned %ld pins, error is %x\n", fetched, (int)result); + + for (unsigned i = 0; i < fetched; i++) { - int direction=-1; + int direction = -1; array[i]->vt->QueryDirection(array[i], (PIN_DIRECTION*)&direction); - if((!m_pInputPin)&&(direction==0)) + if (!m_pInputPin && direction == 0) { - m_pInputPin=array[i]; + m_pInputPin = array[i]; m_pInputPin->vt->AddRef((IUnknown*)m_pInputPin); } - if((!m_pOutputPin)&&(direction==1)) + if (!m_pOutputPin && direction == 1) { - m_pOutputPin=array[i]; + m_pOutputPin = array[i]; m_pOutputPin->vt->AddRef((IUnknown*)m_pOutputPin); } array[i]->vt->Release((IUnknown*)(array[i])); } - if(!m_pInputPin)throw FATAL("Input pin not found"); - if(!m_pOutputPin)throw FATAL("Output pin not found"); - - result=m_pInputPin->vt->QueryInterface((IUnknown*)m_pInputPin, &IID_IMemInputPin, (void**)&m_pImp); + if (!m_pInputPin) + throw FATAL("Input pin not found"); + if (!m_pOutputPin) + throw FATAL("Output pin not found"); + + result = m_pInputPin->vt->QueryInterface((IUnknown*)m_pInputPin, + &IID_IMemInputPin, + (void**)&m_pImp); if(result) throw FATAL("Error getting IMemInputPin interface"); m_pOurType=in_fmt; m_pDestType=out_fmt; result=m_pInputPin->vt->QueryAccept(m_pInputPin, m_pOurType); - if(result) throw FATAL("Source format is not accepted"); + if (result) + throw FATAL("Source format is not accepted"); m_pParentFilter=new CBaseFilter2; m_pSrcFilter=new CBaseFilter(*m_pOurType, m_pParentFilter); m_pOurInput=m_pSrcFilter->GetPin(); m_pOurInput->vt->AddRef((IUnknown*)m_pOurInput); - - result=m_pInputPin->vt->ReceiveConnection(m_pInputPin, m_pOurInput, m_pOurType); - if(result) throw FATAL("Error connecting to input pin"); - - m_pOurOutput=new COutputPin(*m_pDestType); - result=m_pOutputPin->vt->ReceiveConnection(m_pOutputPin, - m_pOurOutput, m_pDestType); - if(result)throw FATAL("Error connecting to output pin"); - m_iState=1; + + result=m_pInputPin->vt->ReceiveConnection(m_pInputPin, m_pOurInput, + m_pOurType); + if (result) + throw FATAL("Error connecting to input pin"); + + m_pOurOutput = new COutputPin(*m_pDestType); + + result = m_pOutputPin->vt->ReceiveConnection(m_pOutputPin, + m_pOurOutput, + m_pDestType); + if (result) + throw FATAL("Error connecting to output pin"); + cout << "Using DirectShow codec: " << dllname << endl; + m_iState = 1; } catch(FatalError e) { e.PrintAll(); - if(m_pFilter)m_pFilter->vt->Release((IUnknown*)m_pFilter); - if(m_pOutputPin)m_pOutputPin->vt->Release((IUnknown*)m_pOutputPin); - if(m_pInputPin)m_pInputPin->vt->Release((IUnknown*)m_pInputPin); - if(m_pImp)m_pImp->vt->Release((IUnknown*)m_pImp); - if(m_pOurInput)m_pOurInput->vt->Release((IUnknown*)m_pOurInput); - delete m_pSrcFilter; - delete m_pParentFilter; - delete m_pOurOutput; - if(m_iHandle)FreeLibrary(m_iHandle); + clean(); throw; } } + void DS_Filter::Start() { - if(m_iState!=1) + if (m_iState != 1) return; - + HRESULT hr=m_pFilter->vt->Run(m_pFilter, 0); - if(hr!=0) + if (hr != 0) { - cerr<<"WARNING: m_Filter->Run() failed, error code "<<hex<<hr<<dec<<endl; + Debug cerr<<"WARNING: m_Filter->Run() failed, error code "<<hex<<hr<<dec<<endl; } hr=m_pImp->vt->GetAllocator(m_pImp, &m_pAll); - if(hr) + if (hr) { - cerr<<"Error getting IMemAllocator interface "<<hex<<hr<<dec<<endl; + Debug cerr<<"Error getting IMemAllocator interface "<<hex<<hr<<dec<<endl; m_pImp->vt->Release((IUnknown*)m_pImp); return; } m_pImp->vt->NotifyAllocator(m_pImp, m_pAll, 0); - m_iState=2; - return; + m_iState = 2; } + void DS_Filter::Stop() { - if(m_iState!=2) - return; - m_pAll->vt->Release((IUnknown*)m_pAll); - m_pAll=0; - m_pFilter->vt->Stop(m_pFilter); - m_iState=1; - return; -} -DS_Filter::~DS_Filter() -{ - if(m_iState==0) - return; - if(m_iState==2)Stop(); - if(m_pInputPin)m_pInputPin->vt->Disconnect(m_pInputPin); - if(m_pOutputPin)m_pOutputPin->vt->Disconnect(m_pOutputPin); - if(m_pFilter)m_pFilter->vt->Release((IUnknown*)m_pFilter); - if(m_pOutputPin)m_pOutputPin->vt->Release((IUnknown*)m_pOutputPin); - if(m_pInputPin)m_pInputPin->vt->Release((IUnknown*)m_pInputPin); - if(m_pOurInput)m_pOurInput->vt->Release((IUnknown*)m_pOurInput); - if(m_pImp)m_pImp->vt->Release((IUnknown*)m_pImp); - delete m_pSrcFilter; - delete m_pParentFilter; - delete m_pOurOutput; - if(m_iHandle)FreeLibrary(m_iHandle); + if (m_iState == 2) + { + m_pAll->vt->Release((IUnknown*)m_pAll); + m_pAll=0; + m_pFilter->vt->Stop(m_pFilter); + m_iState=1; + } } diff --git a/loader/dshow/DS_Filter.h b/loader/dshow/DS_Filter.h index c4aab0d12c..61ddb938fe 100644 --- a/loader/dshow/DS_Filter.h +++ b/loader/dshow/DS_Filter.h @@ -5,18 +5,16 @@ #include "inputpin.h" #include "outputpin.h" #include <string> -using namespace std; + /** User will allocate and fill format structures, call Create(), and then set up m_pAll. **/ class DS_Filter { -protected: public: DS_Filter(); virtual ~DS_Filter(); - void Create(char* dllname, const GUID* id, AM_MEDIA_TYPE* in_fmt, AM_MEDIA_TYPE* out_fmt); void Start(); void Stop(); int m_iHandle; @@ -33,8 +31,11 @@ public: IMemAllocator* m_pAll; IMemInputPin* m_pImp; int m_iState; -protected: -}; -#endif + void Create(char* dllname, const GUID* id, AM_MEDIA_TYPE* in_fmt, AM_MEDIA_TYPE* out_fmt); + void SetPointer(char* pointer); +private: + void clean(); +}; +#endif diff --git a/loader/dshow/DS_VideoDec.c b/loader/dshow/DS_VideoDec.c index de2cc7673e..2d4e8e11f8 100644 --- a/loader/dshow/DS_VideoDec.c +++ b/loader/dshow/DS_VideoDec.c @@ -79,7 +79,7 @@ extern "C" int DS_VideoDecoder_Open(char* dllname, GUID* guid, BITMAPINFOHEADER* memset(&m_obh, 0, sizeof(m_obh)); m_obh.biSize=sizeof(m_obh); - memset(&m_sVhdr, 0, sizeof m_sVhdr); + memset(&m_sVhdr, 0, sizeof(m_sVhdr)); m_sVhdr.bmiHeader=m_bh; m_sVhdr.rcSource.left=m_sVhdr.rcSource.top=0; m_sVhdr.rcSource.right=m_sVhdr.bmiHeader.biWidth; @@ -93,7 +93,7 @@ extern "C" int DS_VideoDecoder_Open(char* dllname, GUID* guid, BITMAPINFOHEADER* m_sOurType.bFixedSizeSamples=false; m_sOurType.bTemporalCompression=true; m_sOurType.pUnk=0; - m_sOurType.cbFormat=sizeof m_sVhdr; + m_sOurType.cbFormat=sizeof(m_sVhdr); m_sOurType.pbFormat=(char*)&m_sVhdr; m_sVhdr2=(VIDEOINFOHEADER*)(new char[sizeof(VIDEOINFOHEADER)+12]); @@ -101,7 +101,7 @@ extern "C" int DS_VideoDecoder_Open(char* dllname, GUID* guid, BITMAPINFOHEADER* m_sVhdr2->bmiHeader.biCompression=0; m_sVhdr2->bmiHeader.biBitCount=24; - memset(&m_sDestType, 0, sizeof m_sDestType); + memset(&m_sDestType, 0, sizeof(m_sDestType)); m_sDestType.majortype=MEDIATYPE_Video; m_sDestType.subtype=MEDIASUBTYPE_RGB24; m_sDestType.formattype=FORMAT_VideoInfo; @@ -119,19 +119,20 @@ extern "C" int DS_VideoDecoder_Open(char* dllname, GUID* guid, BITMAPINFOHEADER* HRESULT result; + dsf=new DS_Filter(); + dsf->Create(dllname, guid, &m_sOurType, &m_sDestType); + if(!flip) { m_sVhdr2->bmiHeader.biHeight*=-1; m_obh.biHeight*=-1; -// result=m_pOutputPin->vt->QueryAccept(m_pOutputPin, &m_sDestType); -// if(result) -// throw FATAL("Decoder does not support upside-down frames"); + result=dsf->m_pOutputPin->vt->QueryAccept(dsf->m_pOutputPin, &m_sDestType); + if(result){ + printf("DShow: Decoder does not support upside-down frames"); + m_obh.biHeight*=-1; + } } - dsf=new DS_Filter(); - - dsf->Create(dllname, guid, &m_sOurType, &m_sDestType); - #if 0 m_sVhdr2->bmiHeader.biBitCount=16; m_sVhdr2->bmiHeader.biCompression=fccYUY2; @@ -182,7 +183,7 @@ extern "C" void DS_VideoDecoder_Start(){ extern "C" void DS_VideoDecoder_Stop(){ if(dsf->m_iState!=2) return; dsf->Stop(); - dsf->m_pOurOutput->SetFramePointer(0); +// dsf->m_pOurOutput->SetFramePointer(0); // free(m_outFrame->data()); //m_outFrame->release();//just in case //m_outFrame=0; diff --git a/loader/dshow/allocator.c b/loader/dshow/allocator.c index 496d56c66f..e4a209626b 100644 --- a/loader/dshow/allocator.c +++ b/loader/dshow/allocator.c @@ -2,6 +2,8 @@ #include "allocator.h" #include <com.h> #define E_NOTIMPL 0x80004001 +using namespace std; + class AllocatorKeeper { public: @@ -36,6 +38,9 @@ MemAllocator::MemAllocator() props.cBuffers=1; props.cbBuffer=65536;/* :/ */ props.cbAlign=props.cbPrefix=0; + + new_pointer=0; + modified_sample=0; } long MemAllocator::CreateAllocator(GUID* clsid, GUID* iid, void** ppv) @@ -131,6 +136,14 @@ HRESULT STDCALL MemAllocator::GetBuffer ( me->used_list.push_back(*it); *ppBuffer=*it; (*ppBuffer)->vt->AddRef((IUnknown*)*ppBuffer); + if(me->new_pointer) + { + if(me->modified_sample) + me->modified_sample->ResetPointer(); + (*it)->SetPointer(me->new_pointer); + me->modified_sample=*it; + me->new_pointer=0; + } me->free_list.remove(*it); return 0; } diff --git a/loader/dshow/allocator.h b/loader/dshow/allocator.h index 0b4917a0a9..4b26c67b79 100644 --- a/loader/dshow/allocator.h +++ b/loader/dshow/allocator.h @@ -6,19 +6,29 @@ #include <list> #include "iunk.h" #include "default.h" -using namespace std; + class MemAllocator: public IMemAllocator { ALLOCATOR_PROPERTIES props; - list<CMediaSample*> used_list; - list<CMediaSample*> free_list; + std::list<CMediaSample*> used_list; + std::list<CMediaSample*> free_list; + char* new_pointer; + CMediaSample* modified_sample; static GUID interfaces[]; DECLARE_IUNKNOWN(MemAllocator) public: MemAllocator(); ~MemAllocator(){delete vt;} static long CreateAllocator(GUID* clsid, GUID* iid, void** ppv); - + void SetPointer(char* pointer) { new_pointer=pointer; } + void ResetPointer() + { + if(modified_sample) + { + modified_sample->ResetPointer(); + modified_sample=0; + } + } static HRESULT STDCALL SetProperties ( IMemAllocator * This, /* [in] */ ALLOCATOR_PROPERTIES *pRequest, diff --git a/loader/dshow/cmediasample.c b/loader/dshow/cmediasample.c index a609a3bc11..677948c4d2 100644 --- a/loader/dshow/cmediasample.c +++ b/loader/dshow/cmediasample.c @@ -33,12 +33,15 @@ CMediaSample::CMediaSample(IMemAllocator* allocator, long _size):refcount(0) isPreroll=0; type_valid=0; block=new char[size]; + old_block=0; Debug printf("%x: Creating media sample with size %d, buffer 0x%x\n", this, _size, block); } CMediaSample::~CMediaSample() { Debug printf("%x: CMediaSample::~CMediaSample() called\n", this); delete vt; + if(old_block) + block=old_block; delete[] block; if(media_type.pbFormat) CoTaskMemFree(media_type.pbFormat); diff --git a/loader/dshow/cmediasample.h b/loader/dshow/cmediasample.h index 3ad91330c7..30d8cea8a8 100644 --- a/loader/dshow/cmediasample.h +++ b/loader/dshow/cmediasample.h @@ -10,6 +10,7 @@ class CMediaSample: public IMediaSample int size; int actual_size; char* block; + char* old_block; int refcount; int isPreroll; int isSyncPoint; @@ -18,6 +19,8 @@ class CMediaSample: public IMediaSample public: CMediaSample(IMemAllocator* allocator, long _size); ~CMediaSample(); + void SetPointer(char* pointer) { old_block=block; block=pointer; } + void ResetPointer() { block=old_block; old_block=0; } static long STDCALL QueryInterface ( IUnknown * This, diff --git a/loader/dshow/guids.c b/loader/dshow/guids.c index c9f9163e21..545282193f 100644 --- a/loader/dshow/guids.c +++ b/loader/dshow/guids.c @@ -55,7 +55,6 @@ GUID MEDIASUBTYPE_YV12={0x32315659, 0x0000, 0x0010, GUID CLSID_MemoryAllocator={0x1e651cc0, 0xb199, 0x11d0, {0x82, 0x12, 0x00, 0xc0, 0x4f, 0xc3, 0x2c, 0x45}}; GUID IID_DivxHidden={0x598eba01, 0xb49a, 0x11d2, - {0xa1, 0xc1, 0x00, 0x60, 0x97, 0x78, 0xaa, 0xaa -}}; + {0xa1, 0xc1, 0x00, 0x60, 0x97, 0x78, 0xaa, 0xaa}}; GUID IID_Iv50Hidden={0x665a4442, 0xd905, 0x11d0, {0xa3, 0x0e, 0x44, 0x45, 0x53, 0x54, 0x00, 0x00}}; diff --git a/loader/dshow/interfaces.h b/loader/dshow/interfaces.h index d88a83b088..c1d8943062 100644 --- a/loader/dshow/interfaces.h +++ b/loader/dshow/interfaces.h @@ -415,4 +415,3 @@ struct IHidden2 struct IHidden2_vt *vt; }; #endif - diff --git a/loader/dshow/outputpin.c b/loader/dshow/outputpin.c index cfb0f32aae..ce1429c37b 100644 --- a/loader/dshow/outputpin.c +++ b/loader/dshow/outputpin.c @@ -1,8 +1,11 @@ + +#include <cstdio> +#include <string> + #include "outputpin.h" -#include <string.h> -#include <stdio.h> #include "allocator.h" #include "iunk.h" + #define E_NOTIMPL 0x80004001 /* An object beyond interface IEnumMediaTypes. @@ -112,7 +115,7 @@ HRESULT STDCALL CEnumMediaTypes::Clone ( COutputPin::COutputPin(const AM_MEDIA_TYPE& vh) :refcount(1), type(vh), remote(0), frame_pointer(0), frame_size_pointer(0) { - IPin::vt=new IPin_vt; + IPin::vt = new IPin_vt; IPin::vt->QueryInterface = QueryInterface; IPin::vt->AddRef = AddRef; IPin::vt->Release = Release; @@ -142,6 +145,15 @@ COutputPin::COutputPin(const AM_MEDIA_TYPE& vh) :refcount(1), type(vh), remote(0 IMemInputPin::vt->Receive = Receive; IMemInputPin::vt->ReceiveMultiple = ReceiveMultiple; IMemInputPin::vt->ReceiveCanBlock = ReceiveCanBlock; + + pAllocator = 0; + frame_pointer = 0; +} + +COutputPin::~COutputPin() +{ + delete IPin::vt; + delete IMemInputPin::vt; } // IPin->IUnknown methods @@ -164,19 +176,22 @@ HRESULT STDCALL COutputPin::QueryInterface(IUnknown* This, GUID* iid, void** ppv } Debug printf("Unknown interface : %08x-%04x-%04x-%02x%02x-" \ - "%02x%02x%02x%02x%02x%02x\n", - iid->f1, iid->f2, iid->f3, - (unsigned char)iid->f4[1], (unsigned char)iid->f4[0], - (unsigned char)iid->f4[2],(unsigned char)iid->f4[3],(unsigned char)iid->f4[4], - (unsigned char)iid->f4[5],(unsigned char)iid->f4[6],(unsigned char)iid->f4[7]); + "%02x%02x%02x%02x%02x%02x\n", + iid->f1, iid->f2, iid->f3, + (unsigned char)iid->f4[1], (unsigned char)iid->f4[0], + (unsigned char)iid->f4[2], (unsigned char)iid->f4[3], + (unsigned char)iid->f4[4], (unsigned char)iid->f4[5], + (unsigned char)iid->f4[6], (unsigned char)iid->f4[7]); return 0x80004002; } + HRESULT STDCALL COutputPin::AddRef(IUnknown* This) { Debug printf("COutputPin::AddRef() called\n"); ((COutputPin*)This)->refcount++; return 0; } + HRESULT STDCALL COutputPin::Release(IUnknown* This) { Debug printf("COutputPin::Release() called\n"); @@ -278,7 +293,6 @@ HRESULT STDCALL COutputPin::QueryId ( return E_NOTIMPL; } - HRESULT STDCALL COutputPin::QueryAccept ( IPin * This, /* [in] */ const AM_MEDIA_TYPE *pmt) @@ -426,6 +440,8 @@ HRESULT STDCALL COutputPin::NotifyAllocator( /* [in] */ int bReadOnly) { Debug printf("COutputPin::NotifyAllocator() called\n"); + COutputPin* pPin=(COutputPin*)This; + pPin->pAllocator=(MemAllocator*)pAllocator; return 0; } @@ -450,7 +466,8 @@ HRESULT STDCALL COutputPin::Receive( int len=pSample->vt->GetActualDataLength(pSample); if(len==0)len=pSample->vt->GetSize(pSample);//for iv50 //if(me.frame_pointer)memcpy(me.frame_pointer, pointer, len); - *me.frame_pointer=pointer; + if(me.frame_pointer) + *me.frame_pointer=pointer; if(me.frame_size_pointer)*me.frame_size_pointer=len; /* FILE* file=fopen("./uncompr.bmp", "wb"); diff --git a/loader/dshow/outputpin.h b/loader/dshow/outputpin.h index f1cc36ee5e..ab516e1506 100644 --- a/loader/dshow/outputpin.h +++ b/loader/dshow/outputpin.h @@ -5,7 +5,7 @@ #include "interfaces.h" #include "guids.h" #include "default.h" - +#include "allocator.h" class COutputPin: public IPin, public IMemInputPin { int refcount; @@ -13,10 +13,12 @@ class COutputPin: public IPin, public IMemInputPin IPin* remote; char** frame_pointer; long* frame_size_pointer; + MemAllocator* pAllocator; public: COutputPin(const AM_MEDIA_TYPE& vhdr); - ~COutputPin(){delete IPin::vt; delete IMemInputPin::vt;} + ~COutputPin(); void SetFramePointer(char** z){frame_pointer=z;} + void SetPointer2(char* p) { if(pAllocator) pAllocator->SetPointer(p); } void SetFrameSizePointer(long* z){frame_size_pointer=z;} void SetNewFormat(const AM_MEDIA_TYPE& a){type=a;} static HRESULT STDCALL QueryInterface(IUnknown* This, GUID* iid, void** ppv); diff --git a/loader/stubs.s b/loader/stubs.s index 519eefa58f..dd2d5db931 100644 --- a/loader/stubs.s +++ b/loader/stubs.s @@ -1,10 +1,10 @@ .file "stubs.c" - .version "01.01" + .version "01.01" gcc2_compiled.: .section .rodata .LC0: .string "Called unk_%s\n" -.text +.data .align 4 .globl unk_exp1 .type unk_exp1,@function diff --git a/loader/win32.c b/loader/win32.c index 59c3cfa153..474192bfef 100644 --- a/loader/win32.c +++ b/loader/win32.c @@ -1577,6 +1577,26 @@ int WINAPI expLoadLibraryA(char* name) { char qq[256]; int result; + char* lastbc; + if (!name) + return -1; + // we skip to the last backslash + // this is effectively eliminating weird characters in + // the text output windows + lastbc = strrchr(name, '\\'); + if (lastbc) + { + int i; + lastbc++; + for (i = 0; 1 ;i++) + { + name[i] = *lastbc++; + if (!name[i]) + break; + } + } +// printf("LoadLibrary wants: %s/%s\n", def_path, name); + if(strncmp(name, "c:\\windows\\", 11)==0)name+=11; if(name[0]!='/') { @@ -1848,10 +1868,10 @@ int expstrlen(char* str) dbgprintf("strlen(0x%x='%s') => %d\n", str, str, result); return result; } -void *expstrcpy(char* str1, const char* str2) +int expstrcpy(char* str1, const char* str2) { - void *result=strcpy(str1, str2); - dbgprintf("strcpy(0x%x, 0x%x='%s') => %p\n", str1, str2, str2, result); + int result= (int) strcpy(str1, str2); + dbgprintf("strcpy(0x%x, 0x%x='%s') => %d\n", str1, str2, str2, result); return result; } int expstrcmp(const char* str1, const char* str2) @@ -1860,17 +1880,23 @@ int expstrcmp(const char* str1, const char* str2) dbgprintf("strcmp(0x%x='%s', 0x%x='%s') => %d\n", str1, str1, str2, str2, result); return result; } -void *expstrcat(char* str1, const char* str2) +int expstrcat(char* str1, const char* str2) { - void *result=strcat(str1, str2); - dbgprintf("strcat(0x%x='%s', 0x%x='%s') => %p\n", str1, str1, str2, str2, result); + int result= (int) strcat(str1, str2); + dbgprintf("strcat(0x%x='%s', 0x%x='%s') => %d\n", str1, str1, str2, str2, result); return result; } -void *expmemmove(void* dest, void* src, int n) +int expisalnum(int c) { - void *result=memmove(dest, src, n); - dbgprintf("memmove(0x%x, 0x%x, %d) => %p\n", dest, src, n, result); - return memmove; + int result= (int) isalnum(c); + dbgprintf("isalnum(0x%x='%c' => %d\n", c, c, result); + return result; +} +int expmemmove(void* dest, void* src, int n) +{ + int result= (int) memmove(dest, src, n); + dbgprintf("memmove(0x%x, 0x%x, %d) => %d\n", dest, src, n, result); + return result; } int expmemcmp(void* dest, void* src, int n) { @@ -1916,6 +1942,16 @@ int WINAPI expIsBadStringPtrW(const short* string, int nchars) if(string)wch_print(string); return result; } + +int WINAPI expIsBadStringPtrA(const char* string, int nchars) +{ + int result; +// if(string==0)result=1; else result=0; +// dbgprintf("IsBadStringPtrW(0x%x, %d) => %d", string, nchars, result); +// if(string)wch_print(string); + return result; +} + extern long WINAPI InterlockedExchangeAdd( long* dest, long incr ) { long ret; @@ -2354,23 +2390,53 @@ WIN_BOOL } - -LONG WINAPI expInterlockedExchange(long *dest, long l) +#if 0 +INT WINAPI expMulDiv(int nNumber,int nNumerator,int nDenominator) { - long retval; - retval = *dest; - *dest = l; - return retval; + return ((long long)nNumber * (long long)nNumerator) / nDenominator; } +#endif -INT WINAPI expMulDiv(int nNumber,int nNumerator,int nDenominator) +int WINAPI expMulDiv(int nNumber, int nNumerator, int nDenominator) { - return ((long long)nNumber * (long long)nNumerator) / nDenominator; + static const long long max_int=0x7FFFFFFFLL; + static const long long min_int=-0x80000000LL; + long long tmp=(long long)nNumber*(long long)nNumerator; + if(!nDenominator)return 1; + tmp/=nDenominator; + if(tmp<min_int) return 1; + if(tmp>max_int) return 1; + return (int)tmp; } +LONG WINAPI explstrcmpiA(const char* str1, const char* str2) +{ + LONG result=strcasecmp(str1, str2); + dbgprintf("strcmpi(0x%x='%s', 0x%x='%s') => %d\n", str1, str1, str2, str2, result); + return result; +} +LONG WINAPI explstrlenA(const char* str1) +{ + LONG result=strlen(str1); + dbgprintf("strlen(0x%x='%s') => %d\n", str1, str1, result); + return result; +} +LONG WINAPI explstrcpyA(char* str1, const char* str2) +{ + int result= (int) strcpy(str1, str2); + dbgprintf("strcpy(0x%x, 0x%x='%s') => %d\n", str1, str2, str2, result); + return result; +} +LONG WINAPI expInterlockedExchange(long *dest, long l) +{ + long retval; + retval = *dest; + *dest = l; + return retval; +} struct exports { @@ -2392,6 +2458,7 @@ struct exports exp_kernel32[]={ FF(IsBadWritePtr, 357) FF(IsBadReadPtr, 354) FF(IsBadStringPtrW, -1) +FF(IsBadStringPtrA, -1) FF(DisableThreadLibraryCalls, -1) FF(CreateThread, -1) FF(CreateEventA, -1) @@ -2497,6 +2564,9 @@ FF(IsProcessorFeaturePresent, -1) FF(GetProcessAffinityMask, -1) FF(InterlockedExchange, -1) FF(MulDiv, -1) +FF(lstrcmpiA, -1) +FF(lstrlenA, -1) +FF(lstrcpyA, -1) }; struct exports exp_msvcrt[]={ @@ -2512,9 +2582,9 @@ FF(strlen, -1) FF(strcpy, -1) FF(strcmp, -1) FF(strcat, -1) +FF(isalnum, -1) FF(memmove, -1) FF(memcmp, -1) -//FF(memcpy, -1) FF(time, -1) }; struct exports exp_winmm[]={ |