nsv.c
上传用户:wstnjxml
上传日期:2014-04-03
资源大小:7248k
文件大小:9k
源码类别:

Windows CE

开发平台:

C/C++

  1. /*****************************************************************************
  2.  *
  3.  * This program is free software ; you can redistribute it and/or modify
  4.  * it under the terms of the GNU General Public License as published by
  5.  * the Free Software Foundation; either version 2 of the License, or
  6.  * (at your option) any later version.
  7.  *
  8.  * This program is distributed in the hope that it will be useful,
  9.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11.  * GNU General Public License for more details.
  12.  *
  13.  * You should have received a copy of the GNU General Public License
  14.  * along with this program; if not, write to the Free Software
  15.  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  16.  *
  17.  * $Id: nsv.c 551 2006-01-09 11:55:09Z picard $
  18.  *
  19.  * The Core Pocket Media Player
  20.  * Copyright (c) 2004-2005 Gabor Kovacs
  21.  *
  22.  ****************************************************************************/
  23. #include "../common/common.h"
  24. #include "nsv.h"
  25. typedef struct nsvstream
  26. {
  27. format_stream Stream;
  28. uint32_t FourCC;
  29. filepos_t FirstPos;
  30. } nsvstream;
  31. typedef struct nsv_t
  32. {
  33. format_base Format;
  34. filepos_t Head;
  35. tick_t FirstTime;
  36. tick_t AVSync;
  37. int AVSyncFrame;
  38. bool_t NeedSync;
  39. uint32_t State;
  40. uint32_t AudioFourCC;
  41. uint32_t VideoFourCC;
  42. int VideoWidth;
  43. int VideoHeight;
  44. fraction VideoRate;
  45. int AuxCount;
  46. int AuxSize;
  47. int AudioSize;
  48. int64_t FrameState;
  49. int Frame;
  50. bool_t FrameValid;
  51. } nsv;
  52. static void Invalid(nsv* p)
  53. {
  54. p->AVSyncFrame = -1;
  55. p->State = 0;
  56. p->AuxCount = 0;
  57. p->AuxSize = 0;
  58. p->AudioSize = 0;
  59. }
  60. static int Init(nsv* p)
  61. {
  62. int i;
  63. format_reader* Reader = p->Format.Reader;
  64. p->Head = 0;
  65. Invalid(p);
  66. for (i=0;i<4;++i)
  67. p->State = (p->State << 8) | Reader->Read8(Reader);
  68. if (p->State == FOURCCBE('N','S','V','f'))
  69. {
  70. uint32_t MetaSize;
  71. uint32_t Duration;
  72. p->Head = Reader->FilePos - 4;
  73. p->Head += Reader->ReadLE32(Reader);
  74. Reader->Skip(Reader,4);
  75. Duration = Reader->ReadLE32(Reader);
  76. if (Duration != (uint32_t)-1)
  77. p->Format.Duration = Scale(Duration,TICKSPERSEC,1000);
  78. MetaSize = Reader->ReadLE32(Reader);
  79. Reader->Skip(Reader,8);
  80. //parse metadata...
  81. Reader->Seek(Reader,p->Head,SEEK_SET);
  82. }
  83. p->Frame = 0;
  84. p->FrameValid = 0;
  85. p->FrameState = 0;
  86. p->AVSyncFrame = -1;
  87. p->NeedSync = 1;
  88. p->FirstTime = 1; // but don't want to return 0
  89. return ERR_NONE;
  90. }
  91. static INLINE bool_t AVCStartSlice(int code,int data)
  92. {
  93. return 0;
  94. }
  95. #define AVC_NAL_SLICE 1
  96. #define AVC_NAL_IDR_SLICE 5
  97. static void CountFrame(nsv* p, const uint8_t* Data, int Len)
  98. {
  99. int i;
  100. int32_t code;
  101. int64_t v = p->FrameState;
  102. switch (p->VideoFourCC)
  103. {
  104. case FOURCC('H','2','6','4'):
  105. for (i=0;i<Len;++i)
  106. {
  107. v = (v<<8) | Data[i];
  108. code = (int32_t)(v>>8) & ~0xE0;
  109. if ((code == 0x100+AVC_NAL_SLICE || code == 0x100+AVC_NAL_IDR_SLICE) && (v & 0x80)==0x80) // bitgolomb()=0 -> slice_pos=0
  110. ++p->Frame;
  111. }
  112. p->FrameValid = 1;
  113. break;
  114. }
  115. p->FrameState = v;
  116. }
  117. static void ReadData(nsv* p, format_reader* Reader, format_packet* Packet, uint32_t FourCC, int Size, int Mode)
  118. {
  119. nsvstream* s = NULL;
  120. int n;
  121. if (FourCC == FOURCC('N','O','N','E') || !FourCC || p->NeedSync)
  122. {
  123. Reader->Skip(Reader,Size);
  124. return;
  125. }
  126. for (n=0;n<p->Format.StreamCount;++n)
  127. {
  128. s = (nsvstream*)p->Format.Streams[n];
  129. if (s->FourCC == FourCC)
  130. break;
  131. }
  132. if (n==p->Format.StreamCount)
  133. {
  134. packetformat Format;
  135. memset(&Format,0,sizeof(Format));
  136. Format.Type = PACKET_NONE;
  137. switch (Mode)
  138. {
  139. case 0:
  140. Format.Type = PACKET_VIDEO;
  141. Format.Format.Video.Width = p->VideoWidth;
  142. Format.Format.Video.Height = p->VideoHeight;
  143. Format.Format.Video.Pixel.Flags = PF_FOURCC | PF_FRAGMENTED;
  144. Format.Format.Video.Pixel.FourCC = UpperFourCC(FourCC);
  145. Format.PacketRate = p->VideoRate;
  146. break;
  147. case 1:
  148. switch (FourCC)
  149. {
  150. case FOURCC('M','P','3',' '):
  151. Format.Type = PACKET_AUDIO;
  152. Format.Format.Audio.Format = AUDIOFMT_MP3;
  153. break;
  154. case FOURCC('A','A','C','P'):
  155. case FOURCC('A','A','C',' '):
  156. Format.Type = PACKET_AUDIO;
  157. Format.Format.Audio.Format = AUDIOFMT_AAC;
  158. break;
  159. case FOURCC('S','P','X',' '):
  160. Format.Type = PACKET_AUDIO;
  161. Format.Format.Audio.Format = AUDIOFMT_SPEEX;
  162. break;
  163. }
  164. break;
  165. case 2:
  166. break;
  167. }
  168. if (Format.Type == PACKET_NONE || (s = (nsvstream*)Format_AddStream(&p->Format,sizeof(nsvstream)))==NULL)
  169. {
  170. Reader->Skip(Reader,Size);
  171. return;
  172. }
  173. s->FourCC = FourCC;
  174. PacketFormatCopy(&s->Stream.Format,&Format);
  175. s->Stream.Fragmented = 1;
  176. s->Stream.DisableDrop = Format.Type = PACKET_AUDIO;
  177. s->FirstPos = -1;
  178. Format_PrepairStream(&p->Format,&s->Stream);
  179. }
  180. if (s->FirstPos<0)
  181. s->FirstPos = Reader->FilePos;
  182. if (p->FrameValid && Mode==0)
  183. Packet->RefTime = p->FirstTime + Scale(p->Frame,TICKSPERSEC*p->VideoRate.Den,p->VideoRate.Num);
  184. else
  185. if (p->FrameValid && Mode==1 && p->AVSyncFrame>=0)
  186. {
  187. Packet->RefTime = p->FirstTime + p->AVSync + Scale(p->AVSyncFrame,TICKSPERSEC*p->VideoRate.Den,p->VideoRate.Num);
  188. p->AVSyncFrame = -1;
  189. }
  190. else
  191. if (Reader->FilePos <= s->FirstPos)
  192. Packet->RefTime = p->FirstTime;
  193. else
  194. Packet->RefTime = TIME_UNKNOWN;
  195. Packet->Data = Reader->ReadAsRef(Reader,Size);
  196. Packet->Stream = &s->Stream;
  197. if (s->Stream.LastTime < TIME_UNKNOWN)
  198. s->Stream.LastTime = TIME_UNKNOWN;
  199. if (Mode==0)
  200. {
  201. format_ref* Ref;
  202. for (Ref=Packet->Data;Ref;Ref=Ref->Next)
  203. CountFrame(p,Ref->Buffer->Block.Ptr + Ref->Begin, Ref->Length);
  204. }
  205. }
  206. static void ReadPayload(nsv* p, format_reader* Reader)
  207. {
  208. int AuxCount = Reader->Read8(Reader);
  209. p->AuxSize = (Reader->ReadLE16(Reader) << 4) + (AuxCount >> 4);
  210. p->AuxCount = AuxCount & 15;
  211. p->AudioSize = Reader->ReadLE16(Reader);
  212. p->State = 0;
  213. if (p->AuxSize > 32768 || p->AuxSize > 0x80000 + p->AuxCount * (0x8000+6))
  214. Invalid(p);
  215. }
  216. static int ReadPacket(nsv* p, format_reader* Reader, format_packet* Packet)
  217. {
  218. filepos_t End = Reader->FilePos + BLOCKSIZE;
  219. while (Reader->FilePos<End)
  220. {
  221. if (p->AuxCount>0)
  222. {
  223. int Size = Reader->ReadLE16(Reader);
  224. if (Size > 32768)
  225. Invalid(p);
  226. else
  227. {
  228. uint32_t FourCC = Reader->ReadLE32(Reader);
  229. ReadData(p,Reader,Packet,FourCC,Size,2);
  230. p->AuxSize -= 6-Size;
  231. --p->AuxCount;
  232. return ERR_NONE;
  233. }
  234. }
  235. else
  236. if (p->AuxSize>0)
  237. {
  238. ReadData(p,Reader,Packet,p->VideoFourCC,p->AuxSize,0);
  239. p->AuxSize = 0;
  240. return ERR_NONE;
  241. }
  242. else
  243. if (p->AudioSize>0)
  244. {
  245. ReadData(p,Reader,Packet,p->AudioFourCC,p->AudioSize,1);
  246. p->AudioSize = 0;
  247. return ERR_NONE;
  248. }
  249. else
  250. if (p->State == FOURCCBE('N','S','V','s'))
  251. {
  252. int FrameRate;
  253. p->VideoFourCC = Reader->ReadLE32(Reader);
  254. p->AudioFourCC = Reader->ReadLE32(Reader);
  255. p->VideoWidth = Reader->ReadLE16(Reader);
  256. p->VideoHeight = Reader->ReadLE16(Reader);
  257. FrameRate = Reader->Read8(Reader);
  258. p->VideoRate.Num = FrameRate;
  259. p->VideoRate.Den = 1;
  260. if (FrameRate & 128)
  261. {
  262. int t = (FrameRate & 127) >> 2;
  263. if (t<16)
  264. {
  265. p->VideoRate.Num = 1;
  266. p->VideoRate.Den = t+1;
  267. }
  268. else
  269. {
  270. p->VideoRate.Num = t-15;
  271. p->VideoRate.Den = 1;
  272. }
  273. switch (FrameRate & 3)
  274. {
  275. case 0:
  276. p->VideoRate.Num *= 30;
  277. break;
  278. case 1:
  279. p->VideoRate.Num *= 30*1000;
  280. p->VideoRate.Den *= 1001;
  281. break;
  282. case 2:
  283. p->VideoRate.Num *= 25;
  284. break;
  285. case 3:
  286. p->VideoRate.Num *= 24*1000;
  287. p->VideoRate.Den *= 1001;
  288. break;
  289. }
  290. }
  291. p->AVSync = Scale((int16_t)Reader->ReadLE16(Reader),TICKSPERSEC,1000);
  292. p->AVSyncFrame = p->Frame;
  293. ReadPayload(p,Reader);
  294. if (p->NeedSync && (p->AuxSize || p->AudioSize))
  295. p->NeedSync = 0;
  296. }
  297. else
  298. if ((p->State & 0xFFFF) == 0xEFBE)
  299. ReadPayload(p,Reader);
  300. else
  301. {
  302. int ch = Reader->Read8(Reader);
  303. if (ch<0)
  304. {
  305. if (Reader->Eof(Reader))
  306. return ERR_END_OF_FILE;
  307. break;
  308. }
  309. p->State = (p->State << 8) + ch;
  310. }
  311. }
  312. return ERR_DATA_NOT_FOUND;
  313. }
  314. static int Seek(nsv* p, tick_t Time, filepos_t FilePos,bool_t PrevKey)
  315. {
  316. int i;
  317. if (FilePos < 0)
  318. {
  319. if (Time>0)
  320. {
  321. if (p->Format.Duration>=0 && p->Format.FileSize>=p->Head)
  322. FilePos = p->Head + Scale(Time,p->Format.FileSize-p->Head,p->Format.Duration);
  323. else
  324. return ERR_NOT_SUPPORTED;
  325. }
  326. else
  327. FilePos = p->Head;
  328. }
  329. Invalid(p);
  330. p->NeedSync = 1;
  331. p->Frame = 0;
  332. p->FrameValid = 0;
  333. p->FrameState = 0;
  334. p->FirstTime = Time>0?Time:TIME_UNKNOWN;
  335. for (i=0;i<p->Format.StreamCount;++i)
  336. ((nsvstream*)p->Format.Streams[i])->FirstPos = -1;
  337. return Format_Seek(&p->Format,FilePos,SEEK_SET);
  338. }
  339. static int Create(nsv* p)
  340. {
  341. p->Format.Init = (fmtfunc)Init;
  342. p->Format.Seek = (fmtseek)Seek;
  343. p->Format.ReadPacket = (fmtreadpacket)ReadPacket;
  344. p->Format.MinHeaderLoad = MINBUFFER/2;
  345. return ERR_NONE;
  346. }
  347. static const nodedef NSV = 
  348. {
  349. sizeof(nsv),
  350. NSV_ID,
  351. FORMATBASE_CLASS,
  352. PRI_DEFAULT,
  353. (nodecreate)Create,
  354. NULL,
  355. };
  356. void NSV_Init()
  357. {
  358.  NodeRegisterClass(&NSV);
  359. }
  360. void NSV_Done()
  361. {
  362. NodeUnRegisterClass(NSV_ID);
  363. }