Upstream version 11.39.250.0
[platform/framework/web/crosswalk.git] / src / net / base / mime_util.cc
index 37e630f..27f3c70 100644 (file)
@@ -924,6 +924,39 @@ void MimeUtil::RemoveProprietaryMediaTypesAndCodecsForTests() {
   allow_proprietary_codecs_ = false;
 }
 
+// Returns true iff |profile_str| conforms to hex string "42y0", where y is one
+// of [8..F]. Requiring constraint_set0_flag be set and profile_idc be 0x42 is
+// taken from ISO-14496-10 7.3.2.1, 7.4.2.1, and Annex A.2.1.
+//
+// |profile_str| is the first four characters of the H.264 suffix string
+// (ignoring the last 2 characters of the full 6 character suffix that are
+// level_idc). From ISO-14496-10 7.3.2.1, it consists of:
+// 8 bits: profile_idc: required to be 0x42 here.
+// 1 bit: constraint_set0_flag : required to be true here.
+// 1 bit: constraint_set1_flag : ignored here.
+// 1 bit: constraint_set2_flag : ignored here.
+// 1 bit: constraint_set3_flag : ignored here.
+// 4 bits: reserved : required to be 0 here.
+//
+// The spec indicates other ways, not implemented here, that a |profile_str|
+// can indicate a baseline conforming decoder is sufficient for decode in Annex
+// A.2.1: "[profile_idc not necessarily 0x42] with constraint_set0_flag set and
+// in which level_idc and constraint_set3_flag represent a level less than or
+// equal to the specified level."
+static bool IsValidH264BaselineProfile(const std::string& profile_str) {
+  uint32 constraint_set_bits;
+  if (profile_str.size() != 4 ||
+      profile_str[0] != '4' ||
+      profile_str[1] != '2' ||
+      profile_str[3] != '0' ||
+      !base::HexStringToUInt(base::StringPiece(profile_str.c_str() + 2, 1),
+                             &constraint_set_bits)) {
+    return false;
+  }
+
+  return constraint_set_bits >= 8;
+}
+
 static bool IsValidH264Level(const std::string& level_str) {
   uint32 level;
   if (level_str.size() != 2 || !base::HexStringToUInt(level_str, &level))
@@ -938,13 +971,16 @@ static bool IsValidH264Level(const std::string& level_str) {
           (level >= 50 && level <= 51));
 }
 
-// Handle parsing H.264 codec IDs as outlined in RFC 6381
-//   avc1.42E0xx - H.264 Baseline
-//   avc1.4D40xx - H.264 Main
-//   avc1.6400xx - H.264 High
+// Handle parsing H.264 codec IDs as outlined in RFC 6381 and ISO-14496-10.
+//   avc1.42y0xx, y >= 8 - H.264 Baseline
+//   avc1.4D40xx         - H.264 Main
+//   avc1.6400xx         - H.264 High
 //
-//   avc1.xxxxxx & avc3.xxxxxx are considered ambiguous forms that
-//   are trying to signal H.264 Baseline.
+//   avc1.xxxxxx & avc3.xxxxxx are considered ambiguous forms that are trying to
+//   signal H.264 Baseline. For example, the idc_level, profile_idc and
+//   constraint_set3_flag pieces may explicitly require decoder to conform to
+//   baseline profile at the specified level (see Annex A and constraint_set0 in
+//   ISO-14496-10).
 static bool ParseH264CodecID(const std::string& codec_id,
                              MimeUtil::Codec* codec,
                              bool* is_ambiguous) {
@@ -956,7 +992,7 @@ static bool ParseH264CodecID(const std::string& codec_id,
   }
 
   std::string profile = StringToUpperASCII(codec_id.substr(5, 4));
-  if (profile == "42E0") {
+  if (IsValidH264BaselineProfile(profile)) {
     *codec = MimeUtil::H264_BASELINE;
   } else if (profile == "4D40") {
     *codec = MimeUtil::H264_MAIN;