DTSAC3Source.cpp
上传用户:xjjlds
上传日期:2015-12-05
资源大小:22823k
文件大小:11k
源码类别:

多媒体编程

开发平台:

Visual C++

  1. /* 
  2.  * Copyright (C) 2003-2005 Gabest
  3.  * http://www.gabest.org
  4.  *
  5.  *  This Program is free software; you can redistribute it and/or modify
  6.  *  it under the terms of the GNU General Public License as published by
  7.  *  the Free Software Foundation; either version 2, or (at your option)
  8.  *  any later version.
  9.  *   
  10.  *  This Program is distributed in the hope that it will be useful,
  11.  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  12.  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13.  *  GNU General Public License for more details.
  14.  *   
  15.  *  You should have received a copy of the GNU General Public License
  16.  *  along with GNU Make; see the file COPYING.  If not, write to
  17.  *  the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. 
  18.  *  http://www.gnu.org/copyleft/gpl.html
  19.  *
  20.  */
  21. #include "stdafx.h"
  22. #include <mmreg.h>
  23. #include <ks.h>
  24. #include <initguid.h>
  25. #include <uuids.h>
  26. #include "........includemoreuuids.h"
  27. #include "dtsac3source.h"
  28. #include "......DSUtilDSUtil.h"
  29. #ifdef REGISTER_FILTER
  30. const AMOVIESETUP_MEDIATYPE sudPinTypesOut[] =
  31. {
  32. {&MEDIATYPE_Audio, &MEDIASUBTYPE_DTS},
  33. {&MEDIATYPE_DVD_ENCRYPTED_PACK, &MEDIASUBTYPE_DTS},
  34. {&MEDIATYPE_Audio, &MEDIASUBTYPE_DOLBY_AC3},
  35. {&MEDIATYPE_DVD_ENCRYPTED_PACK, &MEDIASUBTYPE_DOLBY_AC3},
  36. };
  37. const AMOVIESETUP_PIN sudOpPin[] =
  38. {
  39. {L"Output", FALSE, TRUE, FALSE, FALSE, &CLSID_NULL, NULL, countof(sudPinTypesOut), sudPinTypesOut}
  40. };
  41. const AMOVIESETUP_FILTER sudFilter[] =
  42. {
  43. {&__uuidof(CDTSAC3Source), L"DTS/AC3 Source", MERIT_UNLIKELY, countof(sudOpPin), sudOpPin}
  44. };
  45. CFactoryTemplate g_Templates[] =
  46. {
  47. {sudFilter[0].strName, sudFilter[0].clsID, CreateInstance<CDTSAC3Source>, NULL, &sudFilter[0]}
  48. };
  49. int g_cTemplates = countof(g_Templates);
  50. STDAPI DllRegisterServer()
  51. {
  52. SetRegKeyValue(
  53. _T("Media Type\{e436eb83-524f-11ce-9f53-0020af0ba770}"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"), 
  54. _T("0"), _T("0,4,,7FFE8001"));
  55. SetRegKeyValue(
  56. _T("Media Type\{e436eb83-524f-11ce-9f53-0020af0ba770}"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"), 
  57. _T("1"), _T("0,2,,0B77"));
  58. SetRegKeyValue(
  59. _T("Media Type\{e436eb83-524f-11ce-9f53-0020af0ba770}"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"), 
  60. _T("2"), _T("0,2,,770B"));
  61. SetRegKeyValue(
  62. _T("Media Type\{e436eb83-524f-11ce-9f53-0020af0ba770}"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"), 
  63. _T("Source Filter"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"));
  64. SetRegKeyValue(
  65. _T("Media Type\Extensions"), _T(".dts"), 
  66. _T("Source Filter"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"));
  67. SetRegKeyValue(
  68. _T("Media Type\Extensions"), _T(".ac3"), 
  69. _T("Source Filter"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"));
  70. return AMovieDllRegisterServer2(TRUE);
  71. }
  72. STDAPI DllUnregisterServer()
  73. {
  74. DeleteRegKey(_T("Media Type\{e436eb83-524f-11ce-9f53-0020af0ba770}"), _T("{B4A7BE85-551D-4594-BDC7-832B09185041}"));
  75. DeleteRegKey(_T("Media Type\Extensions"), _T(".dts"));
  76. DeleteRegKey(_T("Media Type\Extensions"), _T(".ac3"));
  77. return AMovieDllRegisterServer2(FALSE);
  78. }
  79. extern "C" BOOL WINAPI DllEntryPoint(HINSTANCE, ULONG, LPVOID);
  80. BOOL APIENTRY DllMain(HANDLE hModule, DWORD dwReason, LPVOID lpReserved)
  81. {
  82.     return DllEntryPoint((HINSTANCE)hModule, dwReason, 0); // "DllMain" of the dshow baseclasses;
  83. }
  84. #endif
  85. //
  86. // CDTSAC3Source
  87. //
  88. CDTSAC3Source::CDTSAC3Source(LPUNKNOWN lpunk, HRESULT* phr)
  89. : CBaseSource<CDTSAC3Stream>(NAME("CDTSAC3Source"), lpunk, phr, __uuidof(this))
  90. {
  91. }
  92. CDTSAC3Source::~CDTSAC3Source()
  93. {
  94. }
  95. // CDTSAC3Stream
  96. CDTSAC3Stream::CDTSAC3Stream(const WCHAR* wfn, CSource* pParent, HRESULT* phr) 
  97. : CBaseStream(NAME("CDTSAC3Stream"), pParent, phr)
  98. , m_nFileOffset(0)
  99. {
  100. CAutoLock cAutoLock(&m_cSharedState);
  101. m_subtype = GUID_NULL;
  102. m_wFormatTag = 0;
  103. m_streamid = 0;
  104. CString fn(wfn);
  105. if(!m_file.Open(fn, CFile::modeRead|CFile::shareDenyWrite))
  106. {
  107. if(phr) *phr = E_FAIL;
  108. return;
  109. }
  110. DWORD id = 0;
  111. if(m_file.Read(&id, sizeof(id)) != sizeof(id)
  112. || id != 0x0180FE7F && (WORD)id != 0x0b77 && (WORD)id != 0x770b)
  113. {
  114. if(phr) *phr = E_FAIL;
  115. return;
  116. }
  117. if(id == 0x0180FE7F)
  118. {
  119. BYTE buff[8];
  120. m_file.Read(buff, 8);
  121. int frametype = (buff[0]>>7); // 1
  122. int deficitsamplecount = (buff[0]>>2)&31; // 5
  123. int crcpresent = (buff[0]>>1)&1; // 1
  124. int npcmsampleblocks = ((buff[0]&1)<<6)|(buff[1]>>2); // 7
  125. int framebytes = (((buff[1]&3)<<12)|(buff[2]<<4)|(buff[3]>>4)) + 1; // 14
  126. int audiochannelarrangement = (buff[3]&15)<<2|(buff[4]>>6); // 6
  127. int freq = (buff[4]>>2)&15; // 4
  128. int transbitrate = ((buff[4]&3)<<3)|(buff[5]>>5); // 5
  129. int freqtbl[] = 
  130. {
  131. 0,8000,16000,32000,
  132. 0,0,
  133. 11025,22050,44100,
  134. 0,0,
  135. 12000,24000,48000,
  136. 0,0
  137. };
  138. int bitratetbl[] = 
  139. {
  140. 32000,56000,64000,96000,112000,128000,192000,224000,
  141. 256000,320000,384000,448000,512000,576000,640000,754500,
  142. 960000,1024000,1152000,1280000,1344000,1408000,1411200,1472000,
  143. 1509750,1920000,2048000,3072000,3840000,0,0,0
  144. };
  145. m_nSamplesPerSec = freqtbl[freq];
  146. m_nAvgBytesPerSec = (bitratetbl[transbitrate] + 4) / 8;
  147. // m_nBytesPerFrame = m_nAvgBytesPerSec*10.656063618290258449304174950298/1000 + 0.5;
  148. m_nBytesPerFrame = framebytes;
  149. m_AvgTimePerFrame = 10000000i64 * m_nBytesPerFrame * 8 / bitratetbl[transbitrate];
  150. m_subtype = MEDIASUBTYPE_DTS;
  151. m_wFormatTag = WAVE_FORMAT_DVD_DTS;
  152. m_streamid = 0x88;
  153. }
  154. else
  155. {
  156. BYTE info;
  157. if((BYTE)id == 0x77) m_file.Seek(1, CFile::current); // LE
  158. m_file.Read(&info, 1);
  159. BYTE freq = info>>6;
  160. BYTE bitrate = info&0x3f;
  161. if(bitrate >= 38)
  162. {
  163. if(phr) *phr = E_FAIL;
  164. return;
  165. }
  166. int freqtbl[] = {48000,44000,32000,48000};
  167. int bitratetbl[] =
  168. {
  169. 32000,32000,40000,40000,48000,48000,56000,56000,64000,64000,
  170. 80000,80000,96000,96000,112000,112000,128000,128000,160000,160000,
  171. 192000,192000,224000,224000,256000,256000,320000,320000,384000,384000,
  172. 448000,448000,512000,512000,576000,576000,640000,640000
  173. };
  174. m_nSamplesPerSec = freqtbl[freq];
  175. m_nAvgBytesPerSec = (bitratetbl[bitrate] + 4) / 8;
  176. m_nBytesPerFrame = m_nAvgBytesPerSec*32/1000;
  177. m_AvgTimePerFrame = 10000000i64 * m_nBytesPerFrame * 8 / bitratetbl[bitrate];
  178. m_subtype = MEDIASUBTYPE_DOLBY_AC3;
  179. m_wFormatTag = WAVE_FORMAT_DOLBY_AC3;
  180. m_streamid = 0x80;
  181. }
  182. m_rtDuration = m_AvgTimePerFrame * m_file.GetLength() / m_nBytesPerFrame;
  183. m_rtStop = m_rtDuration;
  184. }
  185. CDTSAC3Stream::~CDTSAC3Stream()
  186. {
  187. }
  188. HRESULT CDTSAC3Stream::DecideBufferSize(IMemAllocator* pAlloc, ALLOCATOR_PROPERTIES* pProperties)
  189. {
  190.     ASSERT(pAlloc);
  191.     ASSERT(pProperties);
  192.     HRESULT hr = NOERROR;
  193. pProperties->cBuffers = 1;
  194. pProperties->cbBuffer = m_nBytesPerFrame+35;
  195.     ALLOCATOR_PROPERTIES Actual;
  196.     if(FAILED(hr = pAlloc->SetProperties(pProperties, &Actual))) return hr;
  197.     if(Actual.cbBuffer < pProperties->cbBuffer) return E_FAIL;
  198.     ASSERT(Actual.cBuffers == pProperties->cBuffers);
  199.     return NOERROR;
  200. }
  201. HRESULT CDTSAC3Stream::FillBuffer(IMediaSample* pSample, int nFrame, BYTE* pOut, long& len)
  202. {
  203. BYTE* pOutOrg = pOut;
  204. const GUID* majortype = &m_mt.majortype;
  205. const GUID* subtype = &m_mt.subtype;
  206. if(*majortype == MEDIATYPE_DVD_ENCRYPTED_PACK)
  207. {
  208. BYTE PESHeader[] = 
  209. {
  210. 0x00,0x00,0x01,0xBA, // PES id
  211. 0x44,0x00,0x04,0x00,0x04,0x01, // SCR (0)
  212. 0x01,0x89,0xC3,0xF8, // mux rate (1260000 bytes/sec, 22bits), marker (2bits), reserved (~0, 5bits), stuffing (0, 3bits)
  213. };
  214. memcpy(pOut, &PESHeader, sizeof(PESHeader));
  215. pOut += sizeof(PESHeader);
  216. majortype = &MEDIATYPE_MPEG2_PES;
  217. }
  218. if(*majortype == MEDIATYPE_MPEG2_PES)
  219. {
  220. BYTE Private1Header[] = 
  221. {
  222. 0x00,0x00,0x01,0xBD, // private stream 1 id
  223. 0x07,0xEC, // packet length (TODO: modify it later)
  224. 0x81,0x80, // marker, original, PTS - flags
  225. 0x08, // packet data starting offset
  226. 0x21,0x00,0x01,0x00,0x01, // PTS (0)
  227. 0xFF,0xFF,0xFF, // stuffing
  228. m_streamid, // stream id (0)
  229. 0x01,0x00,0x01, // no idea about this (might be the current sector on the disc), but dvd2avi doesn't output it to the ac3/dts file so we have to put it back
  230. };
  231. memcpy(pOut, &Private1Header, sizeof(Private1Header));
  232. pOut += sizeof(Private1Header);
  233. majortype = &MEDIATYPE_Audio;
  234. }
  235. if(*majortype == MEDIATYPE_Audio)
  236. {
  237. m_file.Seek(m_nFileOffset + nFrame*m_nBytesPerFrame, CFile::begin);
  238. if(m_file.Read(pOut, m_nBytesPerFrame) < m_nBytesPerFrame) return S_FALSE;
  239. pOut += m_nBytesPerFrame;
  240. }
  241. len = pOut - pOutOrg;
  242. return S_OK;
  243. }
  244. bool CDTSAC3Stream::CheckDTS(const CMediaType* pmt)
  245. {
  246. return (pmt->majortype == MEDIATYPE_Audio
  247. || pmt->majortype == MEDIATYPE_MPEG2_PES 
  248. || pmt->majortype == MEDIATYPE_DVD_ENCRYPTED_PACK)
  249. && pmt->subtype == MEDIASUBTYPE_DTS;
  250. }
  251. bool CDTSAC3Stream::CheckWAVEDTS(const CMediaType* pmt)
  252. {
  253. return pmt->majortype == MEDIATYPE_Audio
  254. && pmt->subtype == MEDIASUBTYPE_WAVE_DTS
  255. && pmt->formattype == FORMAT_WaveFormatEx
  256. && ((WAVEFORMATEX*)pmt->pbFormat)->wFormatTag == WAVE_FORMAT_DVD_DTS;
  257. }
  258. bool CDTSAC3Stream::CheckAC3(const CMediaType* pmt)
  259. {
  260. return (pmt->majortype == MEDIATYPE_Audio
  261. || pmt->majortype == MEDIATYPE_MPEG2_PES 
  262. || pmt->majortype == MEDIATYPE_DVD_ENCRYPTED_PACK)
  263. && pmt->subtype == MEDIASUBTYPE_DOLBY_AC3;
  264. }
  265. bool CDTSAC3Stream::CheckWAVEAC3(const CMediaType* pmt)
  266. {
  267. return pmt->majortype == MEDIATYPE_Audio
  268. && pmt->subtype == MEDIASUBTYPE_DOLBY_AC3
  269. && pmt->formattype == FORMAT_WaveFormatEx
  270. && ((WAVEFORMATEX*)pmt->pbFormat)->wFormatTag == WAVE_FORMAT_DOLBY_AC3;
  271. }
  272. HRESULT CDTSAC3Stream::GetMediaType(int iPosition, CMediaType* pmt)
  273. {
  274.     CAutoLock cAutoLock(m_pFilter->pStateLock());
  275. if(iPosition >= 0 && iPosition < 5)
  276. {
  277. pmt->subtype = m_subtype;
  278. pmt->formattype = FORMAT_WaveFormatEx;
  279. WAVEFORMATEX* wfe = (WAVEFORMATEX*)pmt->AllocFormatBuffer(sizeof(WAVEFORMATEX));
  280. memset(wfe, 0, sizeof(WAVEFORMATEX));
  281. wfe->cbSize = sizeof(WAVEFORMATEX);
  282. wfe->wFormatTag = WAVE_FORMAT_PCM;
  283. wfe->nSamplesPerSec = m_nSamplesPerSec;
  284. wfe->nAvgBytesPerSec = m_nAvgBytesPerSec;
  285. wfe->nChannels = 6;
  286. switch(iPosition)
  287. {
  288. case 0:
  289. pmt->majortype = MEDIATYPE_Audio;
  290. break;
  291. case 1:
  292. pmt->ResetFormatBuffer();
  293. pmt->formattype = FORMAT_None;
  294. case 2:
  295. pmt->majortype = MEDIATYPE_MPEG2_PES;
  296. break;
  297. case 3:
  298. pmt->ResetFormatBuffer();
  299. pmt->formattype = FORMAT_None;
  300. case 4:
  301. pmt->majortype = MEDIATYPE_DVD_ENCRYPTED_PACK;
  302. break;
  303. default:
  304. return E_INVALIDARG;
  305. }
  306. }
  307. else if(iPosition == 5)
  308. {
  309. pmt->majortype = MEDIATYPE_Audio;
  310. pmt->subtype = FOURCCMap(m_wFormatTag);
  311. pmt->formattype = FORMAT_WaveFormatEx;
  312. WAVEFORMATEX* wfe = (WAVEFORMATEX*)pmt->AllocFormatBuffer(sizeof(WAVEFORMATEX));
  313. memset(wfe, 0, sizeof(WAVEFORMATEX));
  314. wfe->cbSize = sizeof(WAVEFORMATEX);
  315. wfe->wFormatTag = m_wFormatTag;
  316. wfe->nSamplesPerSec = m_nSamplesPerSec;
  317. wfe->nAvgBytesPerSec = m_nAvgBytesPerSec;
  318. wfe->nChannels = 2;
  319. wfe->nBlockAlign = 1;
  320. }
  321. else
  322. {
  323. return VFW_S_NO_MORE_ITEMS;
  324. }
  325.     pmt->SetTemporalCompression(FALSE);
  326. return S_OK;
  327. }
  328. HRESULT CDTSAC3Stream::CheckMediaType(const CMediaType* pmt)
  329. {
  330. return CheckDTS(pmt) || CheckWAVEDTS(pmt)
  331. || CheckAC3(pmt) || CheckWAVEAC3(pmt)
  332. ? S_OK
  333. : E_INVALIDARG;
  334. }