TSCodecMPEG2.cs 7.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208
  1. //============================================================================
  2. // BDInfo - Blu-ray Video and Audio Analysis Tool
  3. // Copyright © 2010 Cinema Squid
  4. //
  5. // This library is free software; you can redistribute it and/or
  6. // modify it under the terms of the GNU Lesser General Public
  7. // License as published by the Free Software Foundation; either
  8. // version 2.1 of the License, or (at your option) any later version.
  9. //
  10. // This library 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 GNU
  13. // Lesser General Public License for more details.
  14. //
  15. // You should have received a copy of the GNU Lesser General Public
  16. // License along with this library; if not, write to the Free Software
  17. // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  18. //=============================================================================
  19. #undef DEBUG
  20. namespace BDInfo
  21. {
  22. public abstract class TSCodecMPEG2
  23. {
  24. public static void Scan(
  25. TSVideoStream stream,
  26. TSStreamBuffer buffer,
  27. ref string tag)
  28. {
  29. int parse = 0;
  30. int pictureParse = 0;
  31. int sequenceHeaderParse = 0;
  32. int extensionParse = 0;
  33. int sequenceExtensionParse = 0;
  34. for (int i = 0; i < buffer.Length; i++)
  35. {
  36. parse = (parse << 8) + buffer.ReadByte();
  37. if (parse == 0x00000100)
  38. {
  39. pictureParse = 2;
  40. }
  41. else if (parse == 0x000001B3)
  42. {
  43. sequenceHeaderParse = 7;
  44. }
  45. else if (sequenceHeaderParse > 0)
  46. {
  47. --sequenceHeaderParse;
  48. switch (sequenceHeaderParse)
  49. {
  50. #if DEBUG
  51. case 6:
  52. break;
  53. case 5:
  54. break;
  55. case 4:
  56. stream.Width =
  57. (int)((parse & 0xFFF000) >> 12);
  58. stream.Height =
  59. (int)(parse & 0xFFF);
  60. break;
  61. case 3:
  62. stream.AspectRatio =
  63. (TSAspectRatio)((parse & 0xF0) >> 4);
  64. switch ((parse & 0xF0) >> 4)
  65. {
  66. case 0: // Forbidden
  67. break;
  68. case 1: // Square
  69. break;
  70. case 2: // 4:3
  71. break;
  72. case 3: // 16:9
  73. break;
  74. case 4: // 2.21:1
  75. break;
  76. default: // Reserved
  77. break;
  78. }
  79. switch (parse & 0xF)
  80. {
  81. case 0: // Forbidden
  82. break;
  83. case 1: // 23.976
  84. stream.FrameRateEnumerator = 24000;
  85. stream.FrameRateDenominator = 1001;
  86. break;
  87. case 2: // 24
  88. stream.FrameRateEnumerator = 24000;
  89. stream.FrameRateDenominator = 1000;
  90. break;
  91. case 3: // 25
  92. stream.FrameRateEnumerator = 25000;
  93. stream.FrameRateDenominator = 1000;
  94. break;
  95. case 4: // 29.97
  96. stream.FrameRateEnumerator = 30000;
  97. stream.FrameRateDenominator = 1001;
  98. break;
  99. case 5: // 30
  100. stream.FrameRateEnumerator = 30000;
  101. stream.FrameRateDenominator = 1000;
  102. break;
  103. case 6: // 50
  104. stream.FrameRateEnumerator = 50000;
  105. stream.FrameRateDenominator = 1000;
  106. break;
  107. case 7: // 59.94
  108. stream.FrameRateEnumerator = 60000;
  109. stream.FrameRateDenominator = 1001;
  110. break;
  111. case 8: // 60
  112. stream.FrameRateEnumerator = 60000;
  113. stream.FrameRateDenominator = 1000;
  114. break;
  115. default: // Reserved
  116. stream.FrameRateEnumerator = 0;
  117. stream.FrameRateDenominator = 0;
  118. break;
  119. }
  120. break;
  121. case 2:
  122. break;
  123. case 1:
  124. break;
  125. #endif
  126. case 0:
  127. #if DEBUG
  128. stream.BitRate =
  129. (((parse & 0xFFFFC0) >> 6) * 200);
  130. #endif
  131. stream.IsVBR = true;
  132. stream.IsInitialized = true;
  133. break;
  134. }
  135. }
  136. else if (pictureParse > 0)
  137. {
  138. --pictureParse;
  139. if (pictureParse == 0)
  140. {
  141. switch ((parse & 0x38) >> 3)
  142. {
  143. case 1:
  144. tag = "I";
  145. break;
  146. case 2:
  147. tag = "P";
  148. break;
  149. case 3:
  150. tag = "B";
  151. break;
  152. default:
  153. break;
  154. }
  155. if (stream.IsInitialized) return;
  156. }
  157. }
  158. else if (parse == 0x000001B5)
  159. {
  160. extensionParse = 1;
  161. }
  162. else if (extensionParse > 0)
  163. {
  164. --extensionParse;
  165. if (extensionParse == 0)
  166. {
  167. if ((parse & 0xF0) == 0x10)
  168. {
  169. sequenceExtensionParse = 1;
  170. }
  171. }
  172. }
  173. else if (sequenceExtensionParse > 0)
  174. {
  175. --sequenceExtensionParse;
  176. #if DEBUG
  177. if (sequenceExtensionParse == 0)
  178. {
  179. uint sequenceExtension =
  180. ((parse & 0x8) >> 3);
  181. if (sequenceExtension == 0)
  182. {
  183. stream.IsInterlaced = true;
  184. }
  185. else
  186. {
  187. stream.IsInterlaced = false;
  188. }
  189. }
  190. #endif
  191. }
  192. }
  193. }
  194. }
  195. }