Merge "media: initialize dequeue counter in buffer info"
diff --git a/cmds/screenrecord/Android.bp b/cmds/screenrecord/Android.bp
new file mode 100644
index 0000000..86476cd
--- /dev/null
+++ b/cmds/screenrecord/Android.bp
@@ -0,0 +1,55 @@
+// Copyright 2013 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+cc_binary {
+    name: "screenrecord",
+
+    srcs: [
+        "screenrecord.cpp",
+        "EglWindow.cpp",
+        "FrameOutput.cpp",
+        "TextRenderer.cpp",
+        "Overlay.cpp",
+        "Program.cpp",
+    ],
+
+    shared_libs: [
+        "libstagefright",
+        "libmedia",
+        "libmedia_omx",
+        "libutils",
+        "libbinder",
+        "libstagefright_foundation",
+        "libjpeg",
+        "libui",
+        "libgui",
+        "libcutils",
+        "liblog",
+        "libEGL",
+        "libGLESv2",
+    ],
+
+    include_dirs: [
+        "frameworks/av/media/libstagefright",
+        "frameworks/av/media/libstagefright/include",
+        "frameworks/native/include/media/openmax",
+    ],
+
+    cflags: [
+        "-Werror",
+        "-Wall",
+        "-Wno-multichar",
+        //"-UNDEBUG",
+    ]
+}
diff --git a/cmds/screenrecord/Android.mk b/cmds/screenrecord/Android.mk
deleted file mode 100644
index 5e83ed6..0000000
--- a/cmds/screenrecord/Android.mk
+++ /dev/null
@@ -1,45 +0,0 @@
-# Copyright 2013 The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-#      http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES := \
-	screenrecord.cpp \
-	EglWindow.cpp \
-	FrameOutput.cpp \
-	TextRenderer.cpp \
-	Overlay.cpp \
-	Program.cpp
-
-LOCAL_SHARED_LIBRARIES := \
-	libstagefright libmedia libmedia_omx libutils libbinder libstagefright_foundation \
-	libjpeg libui libgui libcutils liblog libEGL libGLESv2
-
-LOCAL_C_INCLUDES := \
-	frameworks/av/media/libstagefright \
-	frameworks/av/media/libstagefright/include \
-	frameworks/native/include/media/openmax \
-	external/jpeg
-
-LOCAL_CFLAGS := -Werror -Wall
-LOCAL_CFLAGS += -Wno-multichar
-#LOCAL_CFLAGS += -UNDEBUG
-
-LOCAL_MODULE_TAGS := optional
-
-LOCAL_MODULE:= screenrecord
-
-include $(BUILD_EXECUTABLE)
diff --git a/media/extractors/mp4/ItemTable.cpp b/media/extractors/mp4/ItemTable.cpp
index ca9deab..a462de9 100644
--- a/media/extractors/mp4/ItemTable.cpp
+++ b/media/extractors/mp4/ItemTable.cpp
@@ -47,7 +47,7 @@
             offset(0), size(0), nextTileIndex(0) {}
 
     bool isGrid() const {
-        return type == FOURCC('g', 'r', 'i', 'd');
+        return type == FOURCC("grid");
     }
 
     status_t getNextTileItemId(uint32_t *nextTileItemId, bool reset) {
@@ -222,7 +222,7 @@
 
 struct PitmBox : public FullBox {
     PitmBox(DataSourceBase *source) :
-        FullBox(source, FOURCC('p', 'i', 't', 'm')) {}
+        FullBox(source, FOURCC("pitm")) {}
 
     status_t parse(off64_t offset, size_t size, uint32_t *primaryItemId);
 };
@@ -302,7 +302,7 @@
 
 struct IlocBox : public FullBox {
     IlocBox(DataSourceBase *source, KeyedVector<uint32_t, ItemLoc> *itemLocs) :
-        FullBox(source, FOURCC('i', 'l', 'o', 'c')),
+        FullBox(source, FOURCC("iloc")),
         mItemLocs(itemLocs), mHasConstructMethod1(false) {}
 
     status_t parse(off64_t offset, size_t size);
@@ -496,7 +496,7 @@
     ALOGV("attach reference type 0x%x to item id %d)", type(), mItemId);
 
     switch(type()) {
-    case FOURCC('d', 'i', 'm', 'g'): {
+    case FOURCC("dimg"): {
         ssize_t itemIndex = itemIdToItemMap.indexOfKey(mItemId);
 
         // ignore non-image items
@@ -524,7 +524,7 @@
         }
         break;
     }
-    case FOURCC('t', 'h', 'm', 'b'): {
+    case FOURCC("thmb"): {
         ssize_t itemIndex = itemIdToItemMap.indexOfKey(mItemId);
 
         // ignore non-image items
@@ -553,7 +553,7 @@
         }
         break;
     }
-    case FOURCC('c', 'd', 's', 'c'): {
+    case FOURCC("cdsc"): {
         ssize_t itemIndex = itemIdToExifMap.indexOfKey(mItemId);
 
         // ignore non-exif block items
@@ -574,7 +574,7 @@
         }
         break;
     }
-    case FOURCC('a', 'u', 'x', 'l'): {
+    case FOURCC("auxl"): {
         ssize_t itemIndex = itemIdToItemMap.indexOfKey(mItemId);
 
         // ignore non-image items
@@ -627,7 +627,7 @@
 
 struct IrefBox : public FullBox {
     IrefBox(DataSourceBase *source, Vector<sp<ItemReference> > *itemRefs) :
-        FullBox(source, FOURCC('i', 'r', 'e', 'f')), mRefIdSize(0), mItemRefs(itemRefs) {}
+        FullBox(source, FOURCC("iref")), mRefIdSize(0), mItemRefs(itemRefs) {}
 
     status_t parse(off64_t offset, size_t size);
 
@@ -689,7 +689,7 @@
 
 struct IspeBox : public FullBox, public ItemProperty {
     IspeBox(DataSourceBase *source) :
-        FullBox(source, FOURCC('i', 's', 'p', 'e')), mWidth(0), mHeight(0) {}
+        FullBox(source, FOURCC("ispe")), mWidth(0), mHeight(0) {}
 
     status_t parse(off64_t offset, size_t size) override;
 
@@ -725,7 +725,7 @@
 
 struct HvccBox : public Box, public ItemProperty {
     HvccBox(DataSourceBase *source) :
-        Box(source, FOURCC('h', 'v', 'c', 'C')) {}
+        Box(source, FOURCC("hvcC")) {}
 
     status_t parse(off64_t offset, size_t size) override;
 
@@ -758,7 +758,7 @@
 
 struct IrotBox : public Box, public ItemProperty {
     IrotBox(DataSourceBase *source) :
-        Box(source, FOURCC('i', 'r', 'o', 't')), mAngle(0) {}
+        Box(source, FOURCC("irot")), mAngle(0) {}
 
     status_t parse(off64_t offset, size_t size) override;
 
@@ -787,7 +787,7 @@
 
 struct ColrBox : public Box, public ItemProperty {
     ColrBox(DataSourceBase *source) :
-        Box(source, FOURCC('c', 'o', 'l', 'r')) {}
+        Box(source, FOURCC("colr")) {}
 
     status_t parse(off64_t offset, size_t size) override;
 
@@ -811,11 +811,11 @@
     }
     offset += 4;
     size -= 4;
-    if (colour_type == FOURCC('n', 'c', 'l', 'x')) {
+    if (colour_type == FOURCC("nclx")) {
         return OK;
     }
-    if ((colour_type != FOURCC('r', 'I', 'C', 'C')) &&
-        (colour_type != FOURCC('p', 'r', 'o', 'f'))) {
+    if ((colour_type != FOURCC("rICC")) &&
+        (colour_type != FOURCC("prof"))) {
         return ERROR_MALFORMED;
     }
 
@@ -835,7 +835,7 @@
 
 struct IpmaBox : public FullBox {
     IpmaBox(DataSourceBase *source, Vector<AssociationEntry> *associations) :
-        FullBox(source, FOURCC('i', 'p', 'm', 'a')), mAssociations(associations) {}
+        FullBox(source, FOURCC("ipma")), mAssociations(associations) {}
 
     status_t parse(off64_t offset, size_t size);
 private:
@@ -909,7 +909,7 @@
 
 struct IpcoBox : public Box {
     IpcoBox(DataSourceBase *source, Vector<sp<ItemProperty> > *properties) :
-        Box(source, FOURCC('i', 'p', 'c', 'o')), mItemProperties(properties) {}
+        Box(source, FOURCC("ipco")), mItemProperties(properties) {}
 
     status_t parse(off64_t offset, size_t size);
 protected:
@@ -929,22 +929,22 @@
 status_t IpcoBox::onChunkData(uint32_t type, off64_t offset, size_t size) {
     sp<ItemProperty> itemProperty;
     switch(type) {
-        case FOURCC('h', 'v', 'c', 'C'):
+        case FOURCC("hvcC"):
         {
             itemProperty = new HvccBox(source());
             break;
         }
-        case FOURCC('i', 's', 'p', 'e'):
+        case FOURCC("ispe"):
         {
             itemProperty = new IspeBox(source());
             break;
         }
-        case FOURCC('i', 'r', 'o', 't'):
+        case FOURCC("irot"):
         {
             itemProperty = new IrotBox(source());
             break;
         }
-        case FOURCC('c', 'o', 'l', 'r'):
+        case FOURCC("colr"):
         {
             itemProperty = new ColrBox(source());
             break;
@@ -968,7 +968,7 @@
     IprpBox(DataSourceBase *source,
             Vector<sp<ItemProperty> > *properties,
             Vector<AssociationEntry> *associations) :
-        Box(source, FOURCC('i', 'p', 'r', 'p')),
+        Box(source, FOURCC("iprp")),
         mProperties(properties), mAssociations(associations) {}
 
     status_t parse(off64_t offset, size_t size);
@@ -992,12 +992,12 @@
 
 status_t IprpBox::onChunkData(uint32_t type, off64_t offset, size_t size) {
     switch(type) {
-        case FOURCC('i', 'p', 'c', 'o'):
+        case FOURCC("ipco"):
         {
             IpcoBox ipcoBox(source(), mProperties);
             return ipcoBox.parse(offset, size);
         }
-        case FOURCC('i', 'p', 'm', 'a'):
+        case FOURCC("ipma"):
         {
             IpmaBox ipmaBox(source(), mAssociations);
             return ipmaBox.parse(offset, size);
@@ -1023,7 +1023,7 @@
 
 struct InfeBox : public FullBox {
     InfeBox(DataSourceBase *source) :
-        FullBox(source, FOURCC('i', 'n', 'f', 'e')) {}
+        FullBox(source, FOURCC("infe")) {}
 
     status_t parse(off64_t offset, size_t size, ItemInfo *itemInfo);
 
@@ -1103,7 +1103,7 @@
         }
         ALOGV("item_name %s", item_name.c_str());
 
-        if (item_type == FOURCC('m', 'i', 'm', 'e')) {
+        if (item_type == FOURCC("mime")) {
             String8 content_type;
             if (!parseNullTerminatedString(&offset, &size, &content_type)) {
                 return ERROR_MALFORMED;
@@ -1116,7 +1116,7 @@
                     return ERROR_MALFORMED;
                 }
             }
-        } else if (item_type == FOURCC('u', 'r', 'i', ' ')) {
+        } else if (item_type == FOURCC("uri ")) {
             String8 item_uri_type;
             if (!parseNullTerminatedString(&offset, &size, &item_uri_type)) {
                 return ERROR_MALFORMED;
@@ -1128,7 +1128,7 @@
 
 struct IinfBox : public FullBox {
     IinfBox(DataSourceBase *source, Vector<ItemInfo> *itemInfos) :
-        FullBox(source, FOURCC('i', 'i', 'n', 'f')),
+        FullBox(source, FOURCC("iinf")),
         mItemInfos(itemInfos), mHasGrids(false) {}
 
     status_t parse(off64_t offset, size_t size);
@@ -1178,7 +1178,7 @@
 }
 
 status_t IinfBox::onChunkData(uint32_t type, off64_t offset, size_t size) {
-    if (type != FOURCC('i', 'n', 'f', 'e')) {
+    if (type != FOURCC("infe")) {
         return OK;
     }
 
@@ -1187,7 +1187,7 @@
     status_t err = infeBox.parse(offset, size, &itemInfo);
     if (err == OK) {
         mItemInfos->push_back(itemInfo);
-        mHasGrids |= (itemInfo.itemType == FOURCC('g', 'r', 'i', 'd'));
+        mHasGrids |= (itemInfo.itemType == FOURCC("grid"));
     }
     // InfeBox parse returns ERROR_UNSUPPORTED if the box if an unsupported
     // version. Ignore this error as it's not fatal.
@@ -1213,31 +1213,31 @@
 
 status_t ItemTable::parse(uint32_t type, off64_t data_offset, size_t chunk_data_size) {
     switch(type) {
-        case FOURCC('i', 'l', 'o', 'c'):
+        case FOURCC("iloc"):
         {
             return parseIlocBox(data_offset, chunk_data_size);
         }
-        case FOURCC('i', 'i', 'n', 'f'):
+        case FOURCC("iinf"):
         {
             return parseIinfBox(data_offset, chunk_data_size);
         }
-        case FOURCC('i', 'p', 'r', 'p'):
+        case FOURCC("iprp"):
         {
             return parseIprpBox(data_offset, chunk_data_size);
         }
-        case FOURCC('p', 'i', 't', 'm'):
+        case FOURCC("pitm"):
         {
             return parsePitmBox(data_offset, chunk_data_size);
         }
-        case FOURCC('i', 'd', 'a', 't'):
+        case FOURCC("idat"):
         {
             return parseIdatBox(data_offset, chunk_data_size);
         }
-        case FOURCC('i', 'r', 'e', 'f'):
+        case FOURCC("iref"):
         {
             return parseIrefBox(data_offset, chunk_data_size);
         }
-        case FOURCC('i', 'p', 'r', 'o'):
+        case FOURCC("ipro"):
         {
             ALOGW("ipro box not supported!");
             break;
@@ -1354,9 +1354,9 @@
         //   'grid': derived image from tiles
         //   'hvc1': coded image (or tile)
         //   'Exif': EXIF metadata
-        if (info.itemType != FOURCC('g', 'r', 'i', 'd') &&
-            info.itemType != FOURCC('h', 'v', 'c', '1') &&
-            info.itemType != FOURCC('E', 'x', 'i', 'f')) {
+        if (info.itemType != FOURCC("grid") &&
+            info.itemType != FOURCC("hvc1") &&
+            info.itemType != FOURCC("Exif")) {
             continue;
         }
 
@@ -1379,7 +1379,7 @@
             return ERROR_MALFORMED;
         }
 
-        if (info.itemType == FOURCC('E', 'x', 'i', 'f')) {
+        if (info.itemType == FOURCC("Exif")) {
             // Only add if the Exif data is non-empty. The first 4 bytes contain
             // the offset to TIFF header, which the Exif parser doesn't use.
             if (size > 4) {
diff --git a/media/extractors/mp4/MPEG4Extractor.cpp b/media/extractors/mp4/MPEG4Extractor.cpp
index 21ccf44..eeca629 100644
--- a/media/extractors/mp4/MPEG4Extractor.cpp
+++ b/media/extractors/mp4/MPEG4Extractor.cpp
@@ -306,34 +306,34 @@
 
 static const char *FourCC2MIME(uint32_t fourcc) {
     switch (fourcc) {
-        case FOURCC('m', 'p', '4', 'a'):
+        case FOURCC("mp4a"):
             return MEDIA_MIMETYPE_AUDIO_AAC;
 
-        case FOURCC('s', 'a', 'm', 'r'):
+        case FOURCC("samr"):
             return MEDIA_MIMETYPE_AUDIO_AMR_NB;
 
-        case FOURCC('s', 'a', 'w', 'b'):
+        case FOURCC("sawb"):
             return MEDIA_MIMETYPE_AUDIO_AMR_WB;
 
-        case FOURCC('m', 'p', '4', 'v'):
+        case FOURCC("mp4v"):
             return MEDIA_MIMETYPE_VIDEO_MPEG4;
 
-        case FOURCC('s', '2', '6', '3'):
-        case FOURCC('h', '2', '6', '3'):
-        case FOURCC('H', '2', '6', '3'):
+        case FOURCC("s263"):
+        case FOURCC("h263"):
+        case FOURCC("H263"):
             return MEDIA_MIMETYPE_VIDEO_H263;
 
-        case FOURCC('a', 'v', 'c', '1'):
+        case FOURCC("avc1"):
             return MEDIA_MIMETYPE_VIDEO_AVC;
 
-        case FOURCC('h', 'v', 'c', '1'):
-        case FOURCC('h', 'e', 'v', '1'):
+        case FOURCC("hvc1"):
+        case FOURCC("hev1"):
             return MEDIA_MIMETYPE_VIDEO_HEVC;
 
-        case FOURCC('t', 'w', 'o', 's'):
-        case FOURCC('s', 'o', 'w', 't'):
+        case FOURCC("twos"):
+        case FOURCC("sowt"):
             return MEDIA_MIMETYPE_AUDIO_RAW;
-        case FOURCC('a', 'l', 'a', 'c'):
+        case FOURCC("alac"):
             return MEDIA_MIMETYPE_AUDIO_ALAC;
 
         default:
@@ -731,21 +731,21 @@
 
 static bool underMetaDataPath(const Vector<uint32_t> &path) {
     return path.size() >= 5
-        && path[0] == FOURCC('m', 'o', 'o', 'v')
-        && path[1] == FOURCC('u', 'd', 't', 'a')
-        && path[2] == FOURCC('m', 'e', 't', 'a')
-        && path[3] == FOURCC('i', 'l', 's', 't');
+        && path[0] == FOURCC("moov")
+        && path[1] == FOURCC("udta")
+        && path[2] == FOURCC("meta")
+        && path[3] == FOURCC("ilst");
 }
 
 static bool underQTMetaPath(const Vector<uint32_t> &path, int32_t depth) {
     return path.size() >= 2
-            && path[0] == FOURCC('m', 'o', 'o', 'v')
-            && path[1] == FOURCC('m', 'e', 't', 'a')
+            && path[0] == FOURCC("moov")
+            && path[1] == FOURCC("meta")
             && (depth == 2
             || (depth == 3
-                    && (path[2] == FOURCC('h', 'd', 'l', 'r')
-                    ||  path[2] == FOURCC('i', 'l', 's', 't')
-                    ||  path[2] == FOURCC('k', 'e', 'y', 's'))));
+                    && (path[2] == FOURCC("hdlr")
+                    ||  path[2] == FOURCC("ilst")
+                    ||  path[2] == FOURCC("keys"))));
 }
 
 // Given a time in seconds since Jan 1 1904, produce a human-readable string.
@@ -849,7 +849,7 @@
         ALOGE("b/23540914");
         return ERROR_MALFORMED;
     }
-    if (chunk_type != FOURCC('m', 'd', 'a', 't') && chunk_data_size > kMaxAtomSize) {
+    if (chunk_type != FOURCC("mdat") && chunk_data_size > kMaxAtomSize) {
         char errMsg[100];
         sprintf(errMsg, "%s atom has size %" PRId64, chunk, chunk_data_size);
         ALOGE("%s (b/28615448)", errMsg);
@@ -857,8 +857,8 @@
         return ERROR_MALFORMED;
     }
 
-    if (chunk_type != FOURCC('c', 'p', 'r', 't')
-            && chunk_type != FOURCC('c', 'o', 'v', 'r')
+    if (chunk_type != FOURCC("cprt")
+            && chunk_type != FOURCC("covr")
             && mPath.size() == 5 && underMetaDataPath(mPath)) {
         off64_t stop_offset = *offset + chunk_size;
         *offset = data_offset;
@@ -877,40 +877,40 @@
     }
 
     switch(chunk_type) {
-        case FOURCC('m', 'o', 'o', 'v'):
-        case FOURCC('t', 'r', 'a', 'k'):
-        case FOURCC('m', 'd', 'i', 'a'):
-        case FOURCC('m', 'i', 'n', 'f'):
-        case FOURCC('d', 'i', 'n', 'f'):
-        case FOURCC('s', 't', 'b', 'l'):
-        case FOURCC('m', 'v', 'e', 'x'):
-        case FOURCC('m', 'o', 'o', 'f'):
-        case FOURCC('t', 'r', 'a', 'f'):
-        case FOURCC('m', 'f', 'r', 'a'):
-        case FOURCC('u', 'd', 't', 'a'):
-        case FOURCC('i', 'l', 's', 't'):
-        case FOURCC('s', 'i', 'n', 'f'):
-        case FOURCC('s', 'c', 'h', 'i'):
-        case FOURCC('e', 'd', 't', 's'):
-        case FOURCC('w', 'a', 'v', 'e'):
+        case FOURCC("moov"):
+        case FOURCC("trak"):
+        case FOURCC("mdia"):
+        case FOURCC("minf"):
+        case FOURCC("dinf"):
+        case FOURCC("stbl"):
+        case FOURCC("mvex"):
+        case FOURCC("moof"):
+        case FOURCC("traf"):
+        case FOURCC("mfra"):
+        case FOURCC("udta"):
+        case FOURCC("ilst"):
+        case FOURCC("sinf"):
+        case FOURCC("schi"):
+        case FOURCC("edts"):
+        case FOURCC("wave"):
         {
-            if (chunk_type == FOURCC('m', 'o', 'o', 'v') && depth != 0) {
+            if (chunk_type == FOURCC("moov") && depth != 0) {
                 ALOGE("moov: depth %d", depth);
                 return ERROR_MALFORMED;
             }
 
-            if (chunk_type == FOURCC('m', 'o', 'o', 'v') && mInitCheck == OK) {
+            if (chunk_type == FOURCC("moov") && mInitCheck == OK) {
                 ALOGE("duplicate moov");
                 return ERROR_MALFORMED;
             }
 
-            if (chunk_type == FOURCC('m', 'o', 'o', 'f') && !mMoofFound) {
+            if (chunk_type == FOURCC("moof") && !mMoofFound) {
                 // store the offset of the first segment
                 mMoofFound = true;
                 mMoofOffset = *offset;
             }
 
-            if (chunk_type == FOURCC('s', 't', 'b', 'l')) {
+            if (chunk_type == FOURCC("stbl")) {
                 ALOGV("sampleTable chunk is %" PRIu64 " bytes long.", chunk_size);
 
                 if (mDataSource->flags()
@@ -936,7 +936,7 @@
             }
 
             bool isTrack = false;
-            if (chunk_type == FOURCC('t', 'r', 'a', 'k')) {
+            if (chunk_type == FOURCC("trak")) {
                 if (depth != 1) {
                     ALOGE("trak: depth %d", depth);
                     return ERROR_MALFORMED;
@@ -1010,7 +1010,7 @@
 
                     return OK;
                 }
-            } else if (chunk_type == FOURCC('m', 'o', 'o', 'v')) {
+            } else if (chunk_type == FOURCC("moov")) {
                 mInitCheck = OK;
 
                 return UNKNOWN_ERROR;  // Return a dummy error.
@@ -1018,7 +1018,7 @@
             break;
         }
 
-        case FOURCC('s', 'c', 'h', 'm'):
+        case FOURCC("schm"):
         {
 
             *offset += chunk_size;
@@ -1033,23 +1033,23 @@
             scheme_type = ntohl(scheme_type);
             int32_t mode = kCryptoModeUnencrypted;
             switch(scheme_type) {
-                case FOURCC('c', 'b', 'c', '1'):
+                case FOURCC("cbc1"):
                 {
                     mode = kCryptoModeAesCbc;
                     break;
                 }
-                case FOURCC('c', 'b', 'c', 's'):
+                case FOURCC("cbcs"):
                 {
                     mode = kCryptoModeAesCbc;
                     mLastTrack->subsample_encryption = true;
                     break;
                 }
-                case FOURCC('c', 'e', 'n', 'c'):
+                case FOURCC("cenc"):
                 {
                     mode = kCryptoModeAesCtr;
                     break;
                 }
-                case FOURCC('c', 'e', 'n', 's'):
+                case FOURCC("cens"):
                 {
                     mode = kCryptoModeAesCtr;
                     mLastTrack->subsample_encryption = true;
@@ -1063,7 +1063,7 @@
         }
 
 
-        case FOURCC('e', 'l', 's', 't'):
+        case FOURCC("elst"):
         {
             *offset += chunk_size;
 
@@ -1118,7 +1118,7 @@
             break;
         }
 
-        case FOURCC('f', 'r', 'm', 'a'):
+        case FOURCC("frma"):
         {
             *offset += chunk_size;
 
@@ -1144,7 +1144,7 @@
             // If format type is 'alac', it is necessary to get the parameters
             // from a alac atom spreading behind the frma atom.
             // See 'external/alac/ALACMagicCookieDescription.txt'.
-            if (original_fourcc == FOURCC('a', 'l', 'a', 'c')) {
+            if (original_fourcc == FOURCC("alac")) {
                 // Store ALAC magic cookie (decoder needs it).
                 uint8_t alacInfo[12];
                 data_offset = *offset;
@@ -1154,7 +1154,7 @@
                 }
                 uint32_t size = U32_AT(&alacInfo[0]);
                 if ((size != ALAC_SPECIFIC_INFO_SIZE) ||
-                        (U32_AT(&alacInfo[4]) != FOURCC('a', 'l', 'a', 'c')) ||
+                        (U32_AT(&alacInfo[4]) != FOURCC("alac")) ||
                         (U32_AT(&alacInfo[8]) != 0)) {
                     return ERROR_MALFORMED;
                 }
@@ -1180,7 +1180,7 @@
             break;
         }
 
-        case FOURCC('t', 'e', 'n', 'c'):
+        case FOURCC("tenc"):
         {
             *offset += chunk_size;
 
@@ -1286,7 +1286,7 @@
             break;
         }
 
-        case FOURCC('t', 'k', 'h', 'd'):
+        case FOURCC("tkhd"):
         {
             *offset += chunk_size;
 
@@ -1298,7 +1298,7 @@
             break;
         }
 
-        case FOURCC('t', 'r', 'e', 'f'):
+        case FOURCC("tref"):
         {
             off64_t stop_offset = *offset + chunk_size;
             *offset = data_offset;
@@ -1314,7 +1314,7 @@
             break;
         }
 
-        case FOURCC('t', 'h', 'm', 'b'):
+        case FOURCC("thmb"):
         {
             *offset += chunk_size;
 
@@ -1331,7 +1331,7 @@
             break;
         }
 
-        case FOURCC('p', 's', 's', 'h'):
+        case FOURCC("pssh"):
         {
             *offset += chunk_size;
 
@@ -1367,7 +1367,7 @@
             break;
         }
 
-        case FOURCC('m', 'd', 'h', 'd'):
+        case FOURCC("mdhd"):
         {
             *offset += chunk_size;
 
@@ -1464,7 +1464,7 @@
             break;
         }
 
-        case FOURCC('s', 't', 's', 'd'):
+        case FOURCC("stsd"):
         {
             uint8_t buffer[8];
             if (chunk_data_size < (off64_t)sizeof(buffer)) {
@@ -1516,7 +1516,7 @@
             }
             break;
         }
-        case FOURCC('m', 'e', 't', 't'):
+        case FOURCC("mett"):
         {
             *offset += chunk_size;
 
@@ -1539,16 +1539,16 @@
             break;
         }
 
-        case FOURCC('m', 'p', '4', 'a'):
-        case FOURCC('e', 'n', 'c', 'a'):
-        case FOURCC('s', 'a', 'm', 'r'):
-        case FOURCC('s', 'a', 'w', 'b'):
-        case FOURCC('t', 'w', 'o', 's'):
-        case FOURCC('s', 'o', 'w', 't'):
-        case FOURCC('a', 'l', 'a', 'c'):
+        case FOURCC("mp4a"):
+        case FOURCC("enca"):
+        case FOURCC("samr"):
+        case FOURCC("sawb"):
+        case FOURCC("twos"):
+        case FOURCC("sowt"):
+        case FOURCC("alac"):
         {
-            if (mIsQT && chunk_type == FOURCC('m', 'p', '4', 'a')
-                    && depth >= 1 && mPath[depth - 1] == FOURCC('w', 'a', 'v', 'e')) {
+            if (mIsQT && chunk_type == FOURCC("mp4a")
+                    && depth >= 1 && mPath[depth - 1] == FOURCC("wave")) {
                 // Ignore mp4a embedded in QT wave atom
                 *offset += chunk_size;
                 break;
@@ -1578,7 +1578,7 @@
             off64_t stop_offset = *offset + chunk_size;
             *offset = data_offset + sizeof(buffer);
 
-            if (mIsQT && chunk_type == FOURCC('m', 'p', '4', 'a')) {
+            if (mIsQT && chunk_type == FOURCC("mp4a")) {
                 if (version == 1) {
                     if (mDataSource->readAt(*offset, buffer, 16) < 16) {
                         return ERROR_IO;
@@ -1611,14 +1611,14 @@
                 }
             }
 
-            if (chunk_type != FOURCC('e', 'n', 'c', 'a')) {
+            if (chunk_type != FOURCC("enca")) {
                 // if the chunk type is enca, we'll get the type from the frma box later
                 mLastTrack->meta.setCString(kKeyMIMEType, FourCC2MIME(chunk_type));
                 AdjustChannelsAndRate(chunk_type, &num_channels, &sample_rate);
 
                 if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_RAW, FourCC2MIME(chunk_type))) {
                     mLastTrack->meta.setInt32(kKeyBitsPerSample, sample_size);
-                    if (chunk_type == FOURCC('t', 'w', 'o', 's')) {
+                    if (chunk_type == FOURCC("twos")) {
                         mLastTrack->meta.setInt32(kKeyPcmBigEndian, 1);
                     }
                 }
@@ -1628,7 +1628,7 @@
             mLastTrack->meta.setInt32(kKeyChannelCount, num_channels);
             mLastTrack->meta.setInt32(kKeySampleRate, sample_rate);
 
-            if (chunk_type == FOURCC('a', 'l', 'a', 'c')) {
+            if (chunk_type == FOURCC("alac")) {
 
                 // See 'external/alac/ALACMagicCookieDescription.txt for the detail'.
                 // Store ALAC magic cookie (decoder needs it).
@@ -1640,7 +1640,7 @@
                 }
                 uint32_t size = U32_AT(&alacInfo[0]);
                 if ((size != ALAC_SPECIFIC_INFO_SIZE) ||
-                        (U32_AT(&alacInfo[4]) != FOURCC('a', 'l', 'a', 'c')) ||
+                        (U32_AT(&alacInfo[4]) != FOURCC("alac")) ||
                         (U32_AT(&alacInfo[8]) != 0)) {
                     return ERROR_MALFORMED;
                 }
@@ -1675,14 +1675,14 @@
             break;
         }
 
-        case FOURCC('m', 'p', '4', 'v'):
-        case FOURCC('e', 'n', 'c', 'v'):
-        case FOURCC('s', '2', '6', '3'):
-        case FOURCC('H', '2', '6', '3'):
-        case FOURCC('h', '2', '6', '3'):
-        case FOURCC('a', 'v', 'c', '1'):
-        case FOURCC('h', 'v', 'c', '1'):
-        case FOURCC('h', 'e', 'v', '1'):
+        case FOURCC("mp4v"):
+        case FOURCC("encv"):
+        case FOURCC("s263"):
+        case FOURCC("H263"):
+        case FOURCC("h263"):
+        case FOURCC("avc1"):
+        case FOURCC("hvc1"):
+        case FOURCC("hev1"):
         {
             uint8_t buffer[78];
             if (chunk_data_size < (ssize_t)sizeof(buffer)) {
@@ -1712,7 +1712,7 @@
             if (mLastTrack == NULL)
                 return ERROR_MALFORMED;
 
-            if (chunk_type != FOURCC('e', 'n', 'c', 'v')) {
+            if (chunk_type != FOURCC("encv")) {
                 // if the chunk type is encv, we'll get the type from the frma box later
                 mLastTrack->meta.setCString(kKeyMIMEType, FourCC2MIME(chunk_type));
             }
@@ -1734,8 +1734,8 @@
             break;
         }
 
-        case FOURCC('s', 't', 'c', 'o'):
-        case FOURCC('c', 'o', '6', '4'):
+        case FOURCC("stco"):
+        case FOURCC("co64"):
         {
             if ((mLastTrack == NULL) || (mLastTrack->sampleTable == NULL)) {
                 return ERROR_MALFORMED;
@@ -1754,7 +1754,7 @@
             break;
         }
 
-        case FOURCC('s', 't', 's', 'c'):
+        case FOURCC("stsc"):
         {
             if ((mLastTrack == NULL) || (mLastTrack->sampleTable == NULL))
                 return ERROR_MALFORMED;
@@ -1772,8 +1772,8 @@
             break;
         }
 
-        case FOURCC('s', 't', 's', 'z'):
-        case FOURCC('s', 't', 'z', '2'):
+        case FOURCC("stsz"):
+        case FOURCC("stz2"):
         {
             if ((mLastTrack == NULL) || (mLastTrack->sampleTable == NULL)) {
                 return ERROR_MALFORMED;
@@ -1884,7 +1884,7 @@
             break;
         }
 
-        case FOURCC('s', 't', 't', 's'):
+        case FOURCC("stts"):
         {
             if ((mLastTrack == NULL) || (mLastTrack->sampleTable == NULL))
                 return ERROR_MALFORMED;
@@ -1902,7 +1902,7 @@
             break;
         }
 
-        case FOURCC('c', 't', 't', 's'):
+        case FOURCC("ctts"):
         {
             if ((mLastTrack == NULL) || (mLastTrack->sampleTable == NULL))
                 return ERROR_MALFORMED;
@@ -1920,7 +1920,7 @@
             break;
         }
 
-        case FOURCC('s', 't', 's', 's'):
+        case FOURCC("stss"):
         {
             if ((mLastTrack == NULL) || (mLastTrack->sampleTable == NULL))
                 return ERROR_MALFORMED;
@@ -1939,7 +1939,7 @@
         }
 
         // \xA9xyz
-        case FOURCC(0xA9, 'x', 'y', 'z'):
+        case FOURCC("\251xyz"):
         {
             *offset += chunk_size;
 
@@ -1989,7 +1989,7 @@
             break;
         }
 
-        case FOURCC('e', 's', 'd', 's'):
+        case FOURCC("esds"):
         {
             *offset += chunk_size;
 
@@ -2019,7 +2019,7 @@
                     kKeyESDS, kTypeESDS, &buffer[4], chunk_data_size - 4);
 
             if (mPath.size() >= 2
-                    && mPath[mPath.size() - 2] == FOURCC('m', 'p', '4', 'a')) {
+                    && mPath[mPath.size() - 2] == FOURCC("mp4a")) {
                 // Information from the ESDS must be relied on for proper
                 // setup of sample rate and channel count for MPEG4 Audio.
                 // The generic header appears to only contain generic
@@ -2033,7 +2033,7 @@
                 }
             }
             if (mPath.size() >= 2
-                    && mPath[mPath.size() - 2] == FOURCC('m', 'p', '4', 'v')) {
+                    && mPath[mPath.size() - 2] == FOURCC("mp4v")) {
                 // Check if the video is MPEG2
                 ESDS esds(&buffer[4], chunk_data_size - 4);
 
@@ -2047,7 +2047,7 @@
             break;
         }
 
-        case FOURCC('b', 't', 'r', 't'):
+        case FOURCC("btrt"):
         {
             *offset += chunk_size;
             if (mLastTrack == NULL) {
@@ -2075,7 +2075,7 @@
             break;
         }
 
-        case FOURCC('a', 'v', 'c', 'C'):
+        case FOURCC("avcC"):
         {
             *offset += chunk_size;
 
@@ -2099,7 +2099,7 @@
 
             break;
         }
-        case FOURCC('h', 'v', 'c', 'C'):
+        case FOURCC("hvcC"):
         {
             auto buffer = heapbuffer<uint8_t>(chunk_data_size);
 
@@ -2123,7 +2123,7 @@
             break;
         }
 
-        case FOURCC('d', '2', '6', '3'):
+        case FOURCC("d263"):
         {
             *offset += chunk_size;
             /*
@@ -2157,7 +2157,7 @@
             break;
         }
 
-        case FOURCC('m', 'e', 't', 'a'):
+        case FOURCC("meta"):
         {
             off64_t stop_offset = *offset + chunk_size;
             *offset = data_offset;
@@ -2201,13 +2201,13 @@
             break;
         }
 
-        case FOURCC('i', 'l', 'o', 'c'):
-        case FOURCC('i', 'i', 'n', 'f'):
-        case FOURCC('i', 'p', 'r', 'p'):
-        case FOURCC('p', 'i', 't', 'm'):
-        case FOURCC('i', 'd', 'a', 't'):
-        case FOURCC('i', 'r', 'e', 'f'):
-        case FOURCC('i', 'p', 'r', 'o'):
+        case FOURCC("iloc"):
+        case FOURCC("iinf"):
+        case FOURCC("iprp"):
+        case FOURCC("pitm"):
+        case FOURCC("idat"):
+        case FOURCC("iref"):
+        case FOURCC("ipro"):
         {
             if (mIsHeif) {
                 if (mItemTable == NULL) {
@@ -2223,9 +2223,9 @@
             break;
         }
 
-        case FOURCC('m', 'e', 'a', 'n'):
-        case FOURCC('n', 'a', 'm', 'e'):
-        case FOURCC('d', 'a', 't', 'a'):
+        case FOURCC("mean"):
+        case FOURCC("name"):
+        case FOURCC("data"):
         {
             *offset += chunk_size;
 
@@ -2240,7 +2240,7 @@
             break;
         }
 
-        case FOURCC('m', 'v', 'h', 'd'):
+        case FOURCC("mvhd"):
         {
             *offset += chunk_size;
 
@@ -2292,7 +2292,7 @@
             break;
         }
 
-        case FOURCC('m', 'e', 'h', 'd'):
+        case FOURCC("mehd"):
         {
             *offset += chunk_size;
 
@@ -2336,7 +2336,7 @@
             break;
         }
 
-        case FOURCC('m', 'd', 'a', 't'):
+        case FOURCC("mdat"):
         {
             mMdatFound = true;
 
@@ -2344,7 +2344,7 @@
             break;
         }
 
-        case FOURCC('h', 'd', 'l', 'r'):
+        case FOURCC("hdlr"):
         {
             *offset += chunk_size;
 
@@ -2362,7 +2362,7 @@
             // For the 3GPP file format, the handler-type within the 'hdlr' box
             // shall be 'text'. We also want to support 'sbtl' handler type
             // for a practical reason as various MPEG4 containers use it.
-            if (type == FOURCC('t', 'e', 'x', 't') || type == FOURCC('s', 'b', 't', 'l')) {
+            if (type == FOURCC("text") || type == FOURCC("sbtl")) {
                 if (mLastTrack != NULL) {
                     mLastTrack->meta.setCString(kKeyMIMEType, MEDIA_MIMETYPE_TEXT_3GPP);
                 }
@@ -2371,7 +2371,7 @@
             break;
         }
 
-        case FOURCC('k', 'e', 'y', 's'):
+        case FOURCC("keys"):
         {
             *offset += chunk_size;
 
@@ -2384,7 +2384,7 @@
             break;
         }
 
-        case FOURCC('t', 'r', 'e', 'x'):
+        case FOURCC("trex"):
         {
             *offset += chunk_size;
 
@@ -2403,7 +2403,7 @@
             break;
         }
 
-        case FOURCC('t', 'x', '3', 'g'):
+        case FOURCC("tx3g"):
         {
             if (mLastTrack == NULL)
                 return ERROR_MALFORMED;
@@ -2448,7 +2448,7 @@
             break;
         }
 
-        case FOURCC('c', 'o', 'v', 'r'):
+        case FOURCC("covr"):
         {
             *offset += chunk_size;
 
@@ -2479,12 +2479,12 @@
             break;
         }
 
-        case FOURCC('c', 'o', 'l', 'r'):
+        case FOURCC("colr"):
         {
             *offset += chunk_size;
             // this must be in a VisualSampleEntry box under the Sample Description Box ('stsd')
             // ignore otherwise
-            if (depth >= 2 && mPath[depth - 2] == FOURCC('s', 't', 's', 'd')) {
+            if (depth >= 2 && mPath[depth - 2] == FOURCC("stsd")) {
                 status_t err = parseColorInfo(data_offset, chunk_data_size);
                 if (err != OK) {
                     return err;
@@ -2494,12 +2494,12 @@
             break;
         }
 
-        case FOURCC('t', 'i', 't', 'l'):
-        case FOURCC('p', 'e', 'r', 'f'):
-        case FOURCC('a', 'u', 't', 'h'):
-        case FOURCC('g', 'n', 'r', 'e'):
-        case FOURCC('a', 'l', 'b', 'm'):
-        case FOURCC('y', 'r', 'r', 'c'):
+        case FOURCC("titl"):
+        case FOURCC("perf"):
+        case FOURCC("auth"):
+        case FOURCC("gnre"):
+        case FOURCC("albm"):
+        case FOURCC("yrrc"):
         {
             *offset += chunk_size;
 
@@ -2512,7 +2512,7 @@
             break;
         }
 
-        case FOURCC('I', 'D', '3', '2'):
+        case FOURCC("ID32"):
         {
             *offset += chunk_size;
 
@@ -2525,7 +2525,7 @@
             break;
         }
 
-        case FOURCC('-', '-', '-', '-'):
+        case FOURCC("----"):
         {
             mLastCommentMean.clear();
             mLastCommentName.clear();
@@ -2534,7 +2534,7 @@
             break;
         }
 
-        case FOURCC('s', 'i', 'd', 'x'):
+        case FOURCC("sidx"):
         {
             status_t err = parseSegmentIndex(data_offset, chunk_data_size);
             if (err != OK) {
@@ -2544,13 +2544,13 @@
             return UNKNOWN_ERROR; // stop parsing after sidx
         }
 
-        case FOURCC('a', 'c', '-', '3'):
+        case FOURCC("ac-3"):
         {
             *offset += chunk_size;
             return parseAC3SampleEntry(data_offset);
         }
 
-        case FOURCC('f', 't', 'y', 'p'):
+        case FOURCC("ftyp"):
         {
             if (chunk_data_size < 8 || depth != 0) {
                 return ERROR_MALFORMED;
@@ -2575,16 +2575,16 @@
                 brandSet.insert(brand);
             }
 
-            if (brandSet.count(FOURCC('q', 't', ' ', ' ')) > 0) {
+            if (brandSet.count(FOURCC("qt  ")) > 0) {
                 mIsQT = true;
             } else {
-                if (brandSet.count(FOURCC('m', 'i', 'f', '1')) > 0
-                 && brandSet.count(FOURCC('h', 'e', 'i', 'c')) > 0) {
+                if (brandSet.count(FOURCC("mif1")) > 0
+                 && brandSet.count(FOURCC("heic")) > 0) {
                     ALOGV("identified HEIF image");
 
                     mIsHeif = true;
-                    brandSet.erase(FOURCC('m', 'i', 'f', '1'));
-                    brandSet.erase(FOURCC('h', 'e', 'i', 'c'));
+                    brandSet.erase(FOURCC("mif1"));
+                    brandSet.erase(FOURCC("heic"));
                 }
 
                 if (!brandSet.empty()) {
@@ -2663,7 +2663,7 @@
 
     offset += 4;
     uint32_t type;
-    if (!mDataSource->getUInt32(offset, &type) || type != FOURCC('d', 'a', 'c', '3')) {
+    if (!mDataSource->getUInt32(offset, &type) || type != FOURCC("dac3")) {
         ALOGE("MPEG4Extractor: error while reading ac-3 specific block: header not dac3");
         return ERROR_MALFORMED;
     }
@@ -2867,7 +2867,7 @@
 
         uint32_t type;
         if (!mDataSource->getUInt32(keyOffset + 4, &type)
-                || type != FOURCC('m', 'd', 't', 'a')) {
+                || type != FOURCC("mdta")) {
             return ERROR_MALFORMED;
         }
 
@@ -2909,7 +2909,7 @@
     }
     uint32_t atomFourCC;
     if (!mDataSource->getUInt32(offset + 4, &atomFourCC)
-            || atomFourCC != FOURCC('d', 'a', 't', 'a')) {
+            || atomFourCC != FOURCC("data")) {
         return ERROR_MALFORMED;
     }
     uint32_t dataType;
@@ -3069,52 +3069,48 @@
     MakeFourCCString(mPath[4], chunk);
     ALOGV("meta: %s @ %lld", chunk, (long long)offset);
     switch ((int32_t)mPath[4]) {
-        case FOURCC(0xa9, 'a', 'l', 'b'):
+        case FOURCC("\251alb"):
         {
             metadataKey = kKeyAlbum;
             break;
         }
-        case FOURCC(0xa9, 'A', 'R', 'T'):
+        case FOURCC("\251ART"):
         {
             metadataKey = kKeyArtist;
             break;
         }
-        case FOURCC('a', 'A', 'R', 'T'):
+        case FOURCC("aART"):
         {
             metadataKey = kKeyAlbumArtist;
             break;
         }
-        case FOURCC(0xa9, 'd', 'a', 'y'):
+        case FOURCC("\251day"):
         {
             metadataKey = kKeyYear;
             break;
         }
-        case FOURCC(0xa9, 'n', 'a', 'm'):
+        case FOURCC("\251nam"):
         {
             metadataKey = kKeyTitle;
             break;
         }
-        case FOURCC(0xa9, 'w', 'r', 't'):
+        case FOURCC("\251wrt"):
         {
             metadataKey = kKeyWriter;
             break;
         }
-        case FOURCC('c', 'o', 'v', 'r'):
+        case FOURCC("covr"):
         {
             metadataKey = kKeyAlbumArt;
             break;
         }
-        case FOURCC('g', 'n', 'r', 'e'):
+        case FOURCC("gnre"):
+        case FOURCC("\251gen"):
         {
             metadataKey = kKeyGenre;
             break;
         }
-        case FOURCC(0xa9, 'g', 'e', 'n'):
-        {
-            metadataKey = kKeyGenre;
-            break;
-        }
-        case FOURCC('c', 'p', 'i', 'l'):
+        case FOURCC("cpil"):
         {
             if (size == 9 && flags == 21) {
                 char tmp[16];
@@ -3125,7 +3121,7 @@
             }
             break;
         }
-        case FOURCC('t', 'r', 'k', 'n'):
+        case FOURCC("trkn"):
         {
             if (size == 16 && flags == 0) {
                 char tmp[16];
@@ -3137,7 +3133,7 @@
             }
             break;
         }
-        case FOURCC('d', 'i', 's', 'k'):
+        case FOURCC("disk"):
         {
             if ((size == 14 || size == 16) && flags == 0) {
                 char tmp[16];
@@ -3149,17 +3145,17 @@
             }
             break;
         }
-        case FOURCC('-', '-', '-', '-'):
+        case FOURCC("----"):
         {
             buffer[size] = '\0';
             switch (mPath[5]) {
-                case FOURCC('m', 'e', 'a', 'n'):
+                case FOURCC("mean"):
                     mLastCommentMean.setTo((const char *)buffer + 4);
                     break;
-                case FOURCC('n', 'a', 'm', 'e'):
+                case FOURCC("name"):
                     mLastCommentName.setTo((const char *)buffer + 4);
                     break;
-                case FOURCC('d', 'a', 't', 'a'):
+                case FOURCC("data"):
                     if (size < 8) {
                         delete[] buffer;
                         buffer = NULL;
@@ -3263,12 +3259,12 @@
     }
 
     int32_t type = U32_AT(&buffer[0]);
-    if ((type == FOURCC('n', 'c', 'l', 'x') && size >= 11)
-            || (type == FOURCC('n', 'c', 'l', 'c') && size >= 10)) {
+    if ((type == FOURCC("nclx") && size >= 11)
+            || (type == FOURCC("nclc") && size >= 10)) {
         int32_t primaries = U16_AT(&buffer[4]);
         int32_t transfer = U16_AT(&buffer[6]);
         int32_t coeffs = U16_AT(&buffer[8]);
-        bool fullRange = (type == FOURCC('n', 'c', 'l', 'x')) && (buffer[10] & 128);
+        bool fullRange = (type == FOURCC("nclx")) && (buffer[10] & 128);
 
         ColorAspects aspects;
         ColorUtils::convertIsoColorAspectsToCodecAspects(
@@ -3308,27 +3304,27 @@
 
     uint32_t metadataKey = 0;
     switch (mPath[depth]) {
-        case FOURCC('t', 'i', 't', 'l'):
+        case FOURCC("titl"):
         {
             metadataKey = kKeyTitle;
             break;
         }
-        case FOURCC('p', 'e', 'r', 'f'):
+        case FOURCC("perf"):
         {
             metadataKey = kKeyArtist;
             break;
         }
-        case FOURCC('a', 'u', 't', 'h'):
+        case FOURCC("auth"):
         {
             metadataKey = kKeyWriter;
             break;
         }
-        case FOURCC('g', 'n', 'r', 'e'):
+        case FOURCC("gnre"):
         {
             metadataKey = kKeyGenre;
             break;
         }
-        case FOURCC('a', 'l', 'b', 'm'):
+        case FOURCC("albm"):
         {
             if (buffer[size - 1] != '\0') {
               char tmp[4];
@@ -3340,7 +3336,7 @@
             metadataKey = kKeyAlbum;
             break;
         }
-        case FOURCC('y', 'r', 'r', 'c'):
+        case FOURCC("yrrc"):
         {
             if (size < 6) {
                 delete[] buffer;
@@ -4176,8 +4172,8 @@
 
     switch(chunk_type) {
 
-        case FOURCC('t', 'r', 'a', 'f'):
-        case FOURCC('m', 'o', 'o', 'f'): {
+        case FOURCC("traf"):
+        case FOURCC("moof"): {
             off64_t stop_offset = *offset + chunk_size;
             *offset = data_offset;
             while (*offset < stop_offset) {
@@ -4186,7 +4182,7 @@
                     return err;
                 }
             }
-            if (chunk_type == FOURCC('m', 'o', 'o', 'f')) {
+            if (chunk_type == FOURCC("moof")) {
                 // *offset points to the box following this moof. Find the next moof from there.
 
                 while (true) {
@@ -4215,7 +4211,7 @@
                         return ERROR_MALFORMED;
                     }
 
-                    if (chunk_type == FOURCC('m', 'o', 'o', 'f')) {
+                    if (chunk_type == FOURCC("moof")) {
                         mNextMoofOffset = *offset;
                         break;
                     } else if (chunk_size == 0) {
@@ -4227,7 +4223,7 @@
             break;
         }
 
-        case FOURCC('t', 'f', 'h', 'd'): {
+        case FOURCC("tfhd"): {
                 status_t err;
                 if ((err = parseTrackFragmentHeader(data_offset, chunk_data_size)) != OK) {
                     return err;
@@ -4236,7 +4232,7 @@
                 break;
         }
 
-        case FOURCC('t', 'r', 'u', 'n'): {
+        case FOURCC("trun"): {
                 status_t err;
                 if (mLastParsedTrackId == mTrackId) {
                     if ((err = parseTrackFragmentRun(data_offset, chunk_data_size)) != OK) {
@@ -4248,7 +4244,7 @@
                 break;
         }
 
-        case FOURCC('s', 'a', 'i', 'z'): {
+        case FOURCC("saiz"): {
             status_t err;
             if ((err = parseSampleAuxiliaryInformationSizes(data_offset, chunk_data_size)) != OK) {
                 return err;
@@ -4256,7 +4252,7 @@
             *offset += chunk_size;
             break;
         }
-        case FOURCC('s', 'a', 'i', 'o'): {
+        case FOURCC("saio"): {
             status_t err;
             if ((err = parseSampleAuxiliaryInformationOffsets(data_offset, chunk_data_size)) != OK) {
                 return err;
@@ -4265,7 +4261,7 @@
             break;
         }
 
-        case FOURCC('s', 'e', 'n', 'c'): {
+        case FOURCC("senc"): {
             status_t err;
             if ((err = parseSampleEncryption(data_offset)) != OK) {
                 return err;
@@ -4274,7 +4270,7 @@
             break;
         }
 
-        case FOURCC('m', 'd', 'a', 't'): {
+        case FOURCC("mdat"): {
             // parse DRM info if present
             ALOGV("MPEG4Source::parseChunk mdat");
             // if saiz/saoi was previously observed, do something with the sampleinfos
@@ -5582,27 +5578,27 @@
 
 static bool isCompatibleBrand(uint32_t fourcc) {
     static const uint32_t kCompatibleBrands[] = {
-        FOURCC('i', 's', 'o', 'm'),
-        FOURCC('i', 's', 'o', '2'),
-        FOURCC('a', 'v', 'c', '1'),
-        FOURCC('h', 'v', 'c', '1'),
-        FOURCC('h', 'e', 'v', '1'),
-        FOURCC('3', 'g', 'p', '4'),
-        FOURCC('m', 'p', '4', '1'),
-        FOURCC('m', 'p', '4', '2'),
-        FOURCC('d', 'a', 's', 'h'),
+        FOURCC("isom"),
+        FOURCC("iso2"),
+        FOURCC("avc1"),
+        FOURCC("hvc1"),
+        FOURCC("hev1"),
+        FOURCC("3gp4"),
+        FOURCC("mp41"),
+        FOURCC("mp42"),
+        FOURCC("dash"),
 
         // Won't promise that the following file types can be played.
         // Just give these file types a chance.
-        FOURCC('q', 't', ' ', ' '),  // Apple's QuickTime
-        FOURCC('M', 'S', 'N', 'V'),  // Sony's PSP
+        FOURCC("qt  "),  // Apple's QuickTime
+        FOURCC("MSNV"),  // Sony's PSP
 
-        FOURCC('3', 'g', '2', 'a'),  // 3GPP2
-        FOURCC('3', 'g', '2', 'b'),
-        FOURCC('m', 'i', 'f', '1'),  // HEIF image
-        FOURCC('h', 'e', 'i', 'c'),  // HEIF image
-        FOURCC('m', 's', 'f', '1'),  // HEIF image sequence
-        FOURCC('h', 'e', 'v', 'c'),  // HEIF image sequence
+        FOURCC("3g2a"),  // 3GPP2
+        FOURCC("3g2b"),
+        FOURCC("mif1"),  // HEIF image
+        FOURCC("heic"),  // HEIF image
+        FOURCC("msf1"),  // HEIF image sequence
+        FOURCC("hevc"),  // HEIF image sequence
     };
 
     for (size_t i = 0;
@@ -5669,7 +5665,7 @@
         MakeFourCCString(chunkType, chunkstring);
         ALOGV("saw chunk type %s, size %" PRIu64 " @ %lld", chunkstring, chunkSize, (long long)offset);
         switch (chunkType) {
-            case FOURCC('f', 't', 'y', 'p'):
+            case FOURCC("ftyp"):
             {
                 if (chunkDataSize < 8) {
                     return false;
@@ -5704,7 +5700,7 @@
                 break;
             }
 
-            case FOURCC('m', 'o', 'o', 'v'):
+            case FOURCC("moov"):
             {
                 moovAtomEndOffset = offset + chunkSize;
 
diff --git a/media/extractors/mp4/SampleTable.cpp b/media/extractors/mp4/SampleTable.cpp
index 28fe717..25f8e2a 100644
--- a/media/extractors/mp4/SampleTable.cpp
+++ b/media/extractors/mp4/SampleTable.cpp
@@ -37,13 +37,13 @@
 namespace android {
 
 // static
-const uint32_t SampleTable::kChunkOffsetType32 = FOURCC('s', 't', 'c', 'o');
+const uint32_t SampleTable::kChunkOffsetType32 = FOURCC("stco");
 // static
-const uint32_t SampleTable::kChunkOffsetType64 = FOURCC('c', 'o', '6', '4');
+const uint32_t SampleTable::kChunkOffsetType64 = FOURCC("co64");
 // static
-const uint32_t SampleTable::kSampleSizeType32 = FOURCC('s', 't', 's', 'z');
+const uint32_t SampleTable::kSampleSizeType32 = FOURCC("stsz");
 // static
-const uint32_t SampleTable::kSampleSizeTypeCompact = FOURCC('s', 't', 'z', '2');
+const uint32_t SampleTable::kSampleSizeTypeCompact = FOURCC("stz2");
 
 ////////////////////////////////////////////////////////////////////////////////
 
diff --git a/media/libaudioclient/Android.bp b/media/libaudioclient/Android.bp
index f93d44b..011979e 100644
--- a/media/libaudioclient/Android.bp
+++ b/media/libaudioclient/Android.bp
@@ -42,6 +42,7 @@
     shared_libs: [
         "liblog",
         "libcutils",
+        "libprocessgroup",
         "libutils",
         "libbinder",
         "libdl",
diff --git a/media/libaudioclient/AudioRecord.cpp b/media/libaudioclient/AudioRecord.cpp
index 0aabaf7..8e2da9e 100644
--- a/media/libaudioclient/AudioRecord.cpp
+++ b/media/libaudioclient/AudioRecord.cpp
@@ -26,6 +26,7 @@
 #include <media/AudioRecord.h>
 #include <utils/Log.h>
 #include <private/media/AudioTrackShared.h>
+#include <processgroup/sched_policy.h>
 #include <media/IAudioFlinger.h>
 #include <media/MediaAnalyticsItem.h>
 #include <media/TypeConverter.h>
diff --git a/media/libaudioclient/AudioTrack.cpp b/media/libaudioclient/AudioTrack.cpp
index adeb6a6..a3413e1 100644
--- a/media/libaudioclient/AudioTrack.cpp
+++ b/media/libaudioclient/AudioTrack.cpp
@@ -29,6 +29,7 @@
 #include <media/AudioTrack.h>
 #include <utils/Log.h>
 #include <private/media/AudioTrackShared.h>
+#include <processgroup/sched_policy.h>
 #include <media/IAudioFlinger.h>
 #include <media/AudioParameter.h>
 #include <media/AudioPolicyHelper.h>
@@ -281,6 +282,11 @@
       mPreviousSchedulingGroup(SP_DEFAULT),
       mPausedPosition(0)
 {
+    mAttributes.content_type = AUDIO_CONTENT_TYPE_UNKNOWN;
+    mAttributes.usage = AUDIO_USAGE_UNKNOWN;
+    mAttributes.flags = 0x0;
+    strcpy(mAttributes.tags, "");
+
     (void)set(streamType, sampleRate, format, channelMask,
             frameCount, flags, cbf, user, notificationFrames,
             0 /*sharedBuffer*/, false /*threadCanCallJava*/, sessionId, transferType,
@@ -312,6 +318,11 @@
       mPausedPosition(0),
       mSelectedDeviceId(AUDIO_PORT_HANDLE_NONE)
 {
+    mAttributes.content_type = AUDIO_CONTENT_TYPE_UNKNOWN;
+    mAttributes.usage = AUDIO_USAGE_UNKNOWN;
+    mAttributes.flags = 0x0;
+    strcpy(mAttributes.tags, "");
+
     (void)set(streamType, sampleRate, format, channelMask,
             0 /*frameCount*/, flags, cbf, user, notificationFrames,
             sharedBuffer, false /*threadCanCallJava*/, sessionId, transferType, offloadInfo,
diff --git a/media/libmedia/Android.bp b/media/libmedia/Android.bp
index 2a2d1bc..7deab05 100644
--- a/media/libmedia/Android.bp
+++ b/media/libmedia/Android.bp
@@ -21,6 +21,7 @@
     vndk: {
         enabled: true,
     },
+    double_loadable: true,
     srcs: ["AudioParameter.cpp", "TypeConverter.cpp", "TimeCheck.cpp"],
     cflags: [
         "-Werror",
@@ -202,6 +203,7 @@
         "android.hidl.token@1.0-utils",
         "liblog",
         "libcutils",
+        "libprocessgroup",
         "libutils",
         "libbinder",
         "libsonivox",
diff --git a/media/libmedia/CharacterEncodingDetector.cpp b/media/libmedia/CharacterEncodingDetector.cpp
index 990d260..5c6b981 100644
--- a/media/libmedia/CharacterEncodingDetector.cpp
+++ b/media/libmedia/CharacterEncodingDetector.cpp
@@ -28,6 +28,8 @@
 #include <unicode/ucsdet.h>
 #include <unicode/ustring.h>
 
+#include <cutils/properties.h>
+
 namespace android {
 
 CharacterEncodingDetector::CharacterEncodingDetector() {
@@ -38,6 +40,26 @@
         ALOGE("could not create UConverter for UTF-8");
         mUtf8Conv = NULL;
     }
+
+    // Read system locale setting from system property and map to ICU encoding names.
+    mLocaleEnc = NULL;
+    char locale_value[PROPERTY_VALUE_MAX] = "";
+    if (property_get("persist.sys.locale", locale_value, NULL) > 0) {
+        const size_t len = strnlen(locale_value, sizeof(locale_value));
+
+        if (len == 3 && !strncmp(locale_value, "und", 3)) {
+            // Undetermined
+        } else if (!strncmp(locale_value, "th", 2)) { // Thai
+            mLocaleEnc = "windows-874-2000";
+        }
+        if (mLocaleEnc != NULL) {
+            ALOGV("System locale encoding = %s", mLocaleEnc);
+        } else {
+            ALOGV("Didn't recognize system locale setting, defaulting to en_US");
+        }
+    } else {
+        ALOGV("Couldn't read system locale setting, assuming en_US");
+    }
 }
 
 CharacterEncodingDetector::~CharacterEncodingDetector() {
@@ -157,7 +179,11 @@
                 }
             }
 
-            if (bestCombinedMatch != NULL) {
+            if (mLocaleEnc != NULL && !goodmatch && highest < 50) {
+                combinedenc = mLocaleEnc;
+                ALOGV("confidence is low but we have recognized predefined encoding, "
+                        "so try this (%s) instead", mLocaleEnc);
+            } else if (bestCombinedMatch != NULL) {
                 combinedenc = ucsdet_getName(bestCombinedMatch, &status);
             } else {
                 combinedenc = "ISO-8859-1";
diff --git a/media/libmedia/IMediaMetadataRetriever.cpp b/media/libmedia/IMediaMetadataRetriever.cpp
index 590ba1a..f9fa86e 100644
--- a/media/libmedia/IMediaMetadataRetriever.cpp
+++ b/media/libmedia/IMediaMetadataRetriever.cpp
@@ -23,6 +23,7 @@
 #include <media/IDataSource.h>
 #include <media/IMediaHTTPService.h>
 #include <media/IMediaMetadataRetriever.h>
+#include <processgroup/sched_policy.h>
 #include <utils/String8.h>
 #include <utils/KeyedVector.h>
 
diff --git a/media/libmedia/TypeConverter.cpp b/media/libmedia/TypeConverter.cpp
index a3db754..86def02 100644
--- a/media/libmedia/TypeConverter.cpp
+++ b/media/libmedia/TypeConverter.cpp
@@ -216,6 +216,9 @@
     MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_2POINT1),
     MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_2POINT0POINT2),
     MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_2POINT1POINT2),
+    MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_TRI),
+    MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_TRI_BACK),
+    MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_3POINT1),
     MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_3POINT0POINT2),
     MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_3POINT1POINT2),
     MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_QUAD),
diff --git a/media/libmedia/include/media/CharacterEncodingDetector.h b/media/libmedia/include/media/CharacterEncodingDetector.h
index deaa377..62564b1 100644
--- a/media/libmedia/include/media/CharacterEncodingDetector.h
+++ b/media/libmedia/include/media/CharacterEncodingDetector.h
@@ -54,6 +54,7 @@
         StringArray     mValues;
 
         UConverter*     mUtf8Conv;
+        const char*     mLocaleEnc;
 };
 
 
diff --git a/media/libmediaplayer2/nuplayer2/NuPlayer2.cpp b/media/libmediaplayer2/nuplayer2/NuPlayer2.cpp
index de4f34e..837bbc8 100644
--- a/media/libmediaplayer2/nuplayer2/NuPlayer2.cpp
+++ b/media/libmediaplayer2/nuplayer2/NuPlayer2.cpp
@@ -1884,11 +1884,21 @@
     closeAudioSink();
     mRenderer->flush(true /* audio */, false /* notifyComplete */);
     if (mVideoDecoder != NULL) {
-        mRenderer->flush(false /* audio */, false /* notifyComplete */);
+        mDeferredActions.push_back(
+                new FlushDecoderAction(FLUSH_CMD_NONE /* audio */,
+                                       FLUSH_CMD_FLUSH /* video */));
+        mDeferredActions.push_back(
+                new SeekAction(currentPositionUs,
+                MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC /* mode */));
+        // After a flush without shutdown, decoder is paused.
+        // Don't resume it until source seek is done, otherwise it could
+        // start pulling stale data too soon.
+        mDeferredActions.push_back(new ResumeDecoderAction(false));
+        processDeferredActions();
+    } else {
+        performSeek(currentPositionUs, MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC /* mode */);
     }
 
-    performSeek(currentPositionUs, MediaPlayer2SeekMode::SEEK_PREVIOUS_SYNC /* mode */);
-
     if (forceNonOffload) {
         mRenderer->signalDisableOffloadAudio();
         mOffloadAudio = false;
diff --git a/media/libmediaplayer2/nuplayer2/NuPlayer2Renderer.cpp b/media/libmediaplayer2/nuplayer2/NuPlayer2Renderer.cpp
index fcc7fa5..3d69188 100644
--- a/media/libmediaplayer2/nuplayer2/NuPlayer2Renderer.cpp
+++ b/media/libmediaplayer2/nuplayer2/NuPlayer2Renderer.cpp
@@ -1156,8 +1156,7 @@
         ALOGE("sampleRate is 0 in %s mode", offloadingAudio() ? "offload" : "non-offload");
         return 0;
     }
-    // TODO: remove the (int32_t) casting below as it may overflow at 12.4 hours.
-    return (int64_t)((int32_t)numFrames * 1000000LL / sampleRate);
+    return (int64_t)(numFrames * 1000000LL / sampleRate);
 }
 
 // Calculate duration of pending samples if played at normal rate (i.e., 1.0).
diff --git a/media/libmediaplayerservice/MediaPlayerService.cpp b/media/libmediaplayerservice/MediaPlayerService.cpp
index 9bcfc83..96f79e0 100644
--- a/media/libmediaplayerservice/MediaPlayerService.cpp
+++ b/media/libmediaplayerservice/MediaPlayerService.cpp
@@ -1906,10 +1906,16 @@
         if (AudioSystem::getOutputSamplingRate(&afSampleRate, mStreamType) != NO_ERROR) {
             return NO_INIT;
         }
+        if (afSampleRate == 0) {
+            return NO_INIT;
+        }
         const size_t framesPerBuffer =
                 (unsigned long long)sampleRate * afFrameCount / afSampleRate;
 
         if (bufferCount == 0) {
+            if (framesPerBuffer == 0) {
+                return NO_INIT;
+            }
             // use suggestedFrameCount
             bufferCount = (suggestedFrameCount + framesPerBuffer - 1) / framesPerBuffer;
         }
diff --git a/media/libmediaplayerservice/nuplayer/GenericSource.cpp b/media/libmediaplayerservice/nuplayer/GenericSource.cpp
index 0807896..694235a 100644
--- a/media/libmediaplayerservice/nuplayer/GenericSource.cpp
+++ b/media/libmediaplayerservice/nuplayer/GenericSource.cpp
@@ -94,6 +94,7 @@
     mDisconnected = false;
     mUri.clear();
     mUriHeaders.clear();
+    mSources.clear();
     if (mFd >= 0) {
         close(mFd);
         mFd = -1;
diff --git a/media/libmediaplayerservice/nuplayer/NuPlayer.cpp b/media/libmediaplayerservice/nuplayer/NuPlayer.cpp
index 4b09dda..cf75aec 100644
--- a/media/libmediaplayerservice/nuplayer/NuPlayer.cpp
+++ b/media/libmediaplayerservice/nuplayer/NuPlayer.cpp
@@ -1818,11 +1818,21 @@
     closeAudioSink();
     mRenderer->flush(true /* audio */, false /* notifyComplete */);
     if (mVideoDecoder != NULL) {
-        mRenderer->flush(false /* audio */, false /* notifyComplete */);
+        mDeferredActions.push_back(
+                new FlushDecoderAction(FLUSH_CMD_NONE /* audio */,
+                                       FLUSH_CMD_FLUSH /* video */));
+        mDeferredActions.push_back(
+                new SeekAction(currentPositionUs,
+                MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC /* mode */));
+        // After a flush without shutdown, decoder is paused.
+        // Don't resume it until source seek is done, otherwise it could
+        // start pulling stale data too soon.
+        mDeferredActions.push_back(new ResumeDecoderAction(false));
+        processDeferredActions();
+    } else {
+        performSeek(currentPositionUs, MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC /* mode */);
     }
 
-    performSeek(currentPositionUs, MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC /* mode */);
-
     if (forceNonOffload) {
         mRenderer->signalDisableOffloadAudio();
         mOffloadAudio = false;
diff --git a/media/libmediaplayerservice/nuplayer/NuPlayerDriver.cpp b/media/libmediaplayerservice/nuplayer/NuPlayerDriver.cpp
index 878bd1e..b83e766 100644
--- a/media/libmediaplayerservice/nuplayer/NuPlayerDriver.cpp
+++ b/media/libmediaplayerservice/nuplayer/NuPlayerDriver.cpp
@@ -772,7 +772,7 @@
 
 status_t NuPlayerDriver::getParameter(int key, Parcel *reply) {
 
-    if (key == FOURCC('m','t','r','X')) {
+    if (key == FOURCC('m','t','r','X') && mAnalyticsItem != NULL) {
         // mtrX -- a play on 'metrics' (not matrix)
         // gather current info all together, parcel it, and send it back
         updateMetrics("api");
@@ -1000,7 +1000,7 @@
             // when we have an error, add it to the analytics for this playback.
             // ext1 is our primary 'error type' value. Only add ext2 when non-zero.
             // [test against msg is due to fall through from previous switch value]
-            if (msg == MEDIA_ERROR) {
+            if (msg == MEDIA_ERROR && mAnalyticsItem != NULL) {
                 mAnalyticsItem->setInt32(kPlayerError, ext1);
                 if (ext2 != 0) {
                     mAnalyticsItem->setInt32(kPlayerErrorCode, ext2);
diff --git a/media/libmediaplayerservice/nuplayer/NuPlayerRenderer.cpp b/media/libmediaplayerservice/nuplayer/NuPlayerRenderer.cpp
index be116e3..4992137 100644
--- a/media/libmediaplayerservice/nuplayer/NuPlayerRenderer.cpp
+++ b/media/libmediaplayerservice/nuplayer/NuPlayerRenderer.cpp
@@ -1145,8 +1145,8 @@
         ALOGE("sampleRate is 0 in %s mode", offloadingAudio() ? "offload" : "non-offload");
         return 0;
     }
-    // TODO: remove the (int32_t) casting below as it may overflow at 12.4 hours.
-    return (int64_t)((int32_t)numFrames * 1000000LL / sampleRate);
+
+    return (int64_t)(numFrames * 1000000LL / sampleRate);
 }
 
 // Calculate duration of pending samples if played at normal rate (i.e., 1.0).
diff --git a/media/libstagefright/MediaCodecSource.cpp b/media/libstagefright/MediaCodecSource.cpp
index 0f75822..e22ad0d 100644
--- a/media/libstagefright/MediaCodecSource.cpp
+++ b/media/libstagefright/MediaCodecSource.cpp
@@ -761,8 +761,8 @@
 }
 
 status_t MediaCodecSource::onStart(MetaData *params) {
-    if (mStopping) {
-        ALOGE("Failed to start while we're stopping");
+    if (mStopping || mOutput.lock()->mEncoderReachedEOS) {
+        ALOGE("Failed to start while we're stopping or encoder already stopped due to EOS error");
         return INVALID_OPERATION;
     }
     int64_t startTimeUs;
diff --git a/media/libstagefright/omx/Android.bp b/media/libstagefright/omx/Android.bp
index 8a76de3..10b95d9 100644
--- a/media/libstagefright/omx/Android.bp
+++ b/media/libstagefright/omx/Android.bp
@@ -88,6 +88,7 @@
     vndk: {
         enabled: true,
     },
+    double_loadable: true,
     srcs: ["OMXUtils.cpp"],
     export_include_dirs: [
         "include",
diff --git a/media/libstagefright/xmlparser/Android.bp b/media/libstagefright/xmlparser/Android.bp
index b55dbb0..edd8fbc 100644
--- a/media/libstagefright/xmlparser/Android.bp
+++ b/media/libstagefright/xmlparser/Android.bp
@@ -4,6 +4,7 @@
     vndk: {
         enabled: true,
     },
+    double_loadable: true,
 
     srcs: [
         "MediaCodecsXmlParser.cpp",
diff --git a/media/mediaserver/Android.bp b/media/mediaserver/Android.bp
new file mode 100644
index 0000000..16c7be9
--- /dev/null
+++ b/media/mediaserver/Android.bp
@@ -0,0 +1,46 @@
+
+cc_library_static {
+    name: "libregistermsext",
+    srcs: ["register.cpp"],
+
+    cflags: [
+        "-Werror",
+        "-Wall",
+    ],
+}
+
+cc_binary {
+    name: "mediaserver",
+
+    srcs: ["main_mediaserver.cpp"],
+
+    shared_libs: [
+        "libresourcemanagerservice",
+        "liblog",
+        "libmediaplayerservice",
+        "libutils",
+        "libbinder",
+        "libandroidicu",
+        "android.hardware.media.omx@1.0",
+    ],
+
+    static_libs: [
+        "libicuandroid_utils",
+        "libregistermsext",
+    ],
+
+    include_dirs: [
+        "frameworks/av/media/libmediaplayerservice",
+        "frameworks/av/services/mediaresourcemanager",
+    ],
+
+    compile_multilib: "32",
+
+    init_rc: ["mediaserver.rc"],
+
+    cflags: [
+        "-Werror",
+        "-Wall",
+    ],
+
+}
diff --git a/media/mediaserver/Android.mk b/media/mediaserver/Android.mk
deleted file mode 100644
index 1fbb85e..0000000
--- a/media/mediaserver/Android.mk
+++ /dev/null
@@ -1,41 +0,0 @@
-LOCAL_PATH:= $(call my-dir)
-
-ifneq ($(BOARD_USE_CUSTOM_MEDIASERVEREXTENSIONS),true)
-include $(CLEAR_VARS)
-LOCAL_SRC_FILES := register.cpp
-LOCAL_MODULE := libregistermsext
-LOCAL_MODULE_TAGS := optional
-LOCAL_CFLAGS := -Werror -Wall
-include $(BUILD_STATIC_LIBRARY)
-endif
-
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES:= \
-        main_mediaserver.cpp
-
-LOCAL_SHARED_LIBRARIES := \
-        libresourcemanagerservice \
-        liblog \
-        libmediaplayerservice \
-        libutils \
-        libbinder \
-        libandroidicu \
-        android.hardware.media.omx@1.0 \
-
-LOCAL_STATIC_LIBRARIES := \
-        libicuandroid_utils \
-        libregistermsext
-
-LOCAL_C_INCLUDES := \
-        frameworks/av/media/libmediaplayerservice \
-        frameworks/av/services/mediaresourcemanager \
-
-LOCAL_MODULE:= mediaserver
-LOCAL_32_BIT_ONLY := true
-
-LOCAL_INIT_RC := mediaserver.rc
-
-LOCAL_CFLAGS := -Werror -Wall
-
-include $(BUILD_EXECUTABLE)
diff --git a/media/mediaserver/mediaserver.rc b/media/mediaserver/mediaserver.rc
index f6c325c..8cfcd79 100644
--- a/media/mediaserver/mediaserver.rc
+++ b/media/mediaserver/mediaserver.rc
@@ -2,5 +2,7 @@
     class main
     user media
     group audio camera inet net_bt net_bt_admin net_bw_acct drmrpc mediadrm
+    # TODO(b/123275379): Remove updatable when http://aosp/878198 has landed
+    updatable
     ioprio rt 4
     writepid /dev/cpuset/foreground/tasks /dev/stune/foreground/tasks
diff --git a/media/mtp/IMtpDatabase.h b/media/mtp/IMtpDatabase.h
index 1245092..81fa60c 100644
--- a/media/mtp/IMtpDatabase.h
+++ b/media/mtp/IMtpDatabase.h
@@ -112,8 +112,8 @@
                                             MtpObjectHandle handle, bool succeeded) = 0;
 
     virtual MtpResponseCode         beginCopyObject(MtpObjectHandle handle, MtpObjectHandle newParent,
-                                            MtpStorageID newStorage);
-    virtual void                    endCopyObject(MtpObjectHandle handle, bool succeeded);
+                                            MtpStorageID newStorage) = 0;
+    virtual void                    endCopyObject(MtpObjectHandle handle, bool succeeded) = 0;
 };
 
 }; // namespace android
diff --git a/media/ndk/Android.bp b/media/ndk/Android.bp
index c70d807..1b8ddd9 100644
--- a/media/ndk/Android.bp
+++ b/media/ndk/Android.bp
@@ -95,6 +95,10 @@
         symbol_file: "libmediandk.map.txt",
         versions: ["29"],
     },
+
+    // Bug: http://b/124522995 libmediandk has linker errors when built with
+    // coverage
+    native_coverage: false,
 }
 
 llndk_library {
diff --git a/services/audiopolicy/config/hearing_aid_audio_policy_configuration.xml b/services/audiopolicy/config/hearing_aid_audio_policy_configuration.xml
index 3c48e88..e6e6bdb 100644
--- a/services/audiopolicy/config/hearing_aid_audio_policy_configuration.xml
+++ b/services/audiopolicy/config/hearing_aid_audio_policy_configuration.xml
@@ -2,7 +2,7 @@
 <!-- Hearing aid Audio HAL Audio Policy Configuration file -->
 <module name="hearing_aid" halVersion="2.0">
     <mixPorts>
-        <mixPort name="hearing aid output" role="source" flags="AUDIO_OUTPUT_FLAG_PRIMARY">
+        <mixPort name="hearing aid output" role="source">
             <profile name="" format="AUDIO_FORMAT_PCM_16_BIT"
                      samplingRates="24000,16000"
                      channelMasks="AUDIO_CHANNEL_OUT_STEREO"/>
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
index 23cc02e..5dbd5b3 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
@@ -33,6 +33,8 @@
 #define AUDIO_POLICY_XML_CONFIG_FILE_NAME "audio_policy_configuration.xml"
 #define AUDIO_POLICY_A2DP_OFFLOAD_DISABLED_XML_CONFIG_FILE_NAME \
         "audio_policy_configuration_a2dp_offload_disabled.xml"
+#define AUDIO_POLICY_BLUETOOTH_HAL_ENABLED_XML_CONFIG_FILE_NAME \
+        "audio_policy_configuration_bluetooth_hal_enabled.xml"
 
 #include <inttypes.h>
 #include <math.h>
@@ -2255,10 +2257,11 @@
                                                   audio_devices_t device)
 {
 
-    // VOICE_CALL stream has minVolumeIndex > 0  but can be muted directly by an
-    // app that has MODIFY_PHONE_STATE permission.
+    // VOICE_CALL and BLUETOOTH_SCO stream have minVolumeIndex > 0 but
+    // can be muted directly by an app that has MODIFY_PHONE_STATE permission.
     if (((index < mVolumeCurves->getVolumeIndexMin(stream)) &&
-            !(stream == AUDIO_STREAM_VOICE_CALL && index == 0)) ||
+            !((stream == AUDIO_STREAM_VOICE_CALL || stream == AUDIO_STREAM_BLUETOOTH_SCO) &&
+            index == 0)) ||
             (index > mVolumeCurves->getVolumeIndexMax(stream))) {
         return BAD_VALUE;
     }
@@ -3904,10 +3907,18 @@
     std::vector<const char*> fileNames;
     status_t ret;
 
-    if (property_get_bool("ro.bluetooth.a2dp_offload.supported", false) &&
-        property_get_bool("persist.bluetooth.a2dp_offload.disabled", false)) {
-        // A2DP offload supported but disabled: try to use special XML file
-        fileNames.push_back(AUDIO_POLICY_A2DP_OFFLOAD_DISABLED_XML_CONFIG_FILE_NAME);
+    if (property_get_bool("ro.bluetooth.a2dp_offload.supported", false)) {
+        if (property_get_bool("persist.bluetooth.a2dp_offload.disabled", false)) {
+            fileNames.push_back(AUDIO_POLICY_A2DP_OFFLOAD_DISABLED_XML_CONFIG_FILE_NAME);
+        } else if (property_get_bool("persist.bluetooth.bluetooth_audio_hal.enabled", false)) {
+            // This property persist.bluetooth.bluetooth_audio_hal.enabled is temporary only.
+            // xml files AUDIO_POLICY_BLUETOOTH_HAL_ENABLED_XML_CONFIG_FILE_NAME, although having
+            // the same name, must be different in offload and non offload cases in device
+            // specific configuration file.
+            fileNames.push_back(AUDIO_POLICY_BLUETOOTH_HAL_ENABLED_XML_CONFIG_FILE_NAME);
+        }
+    } else if (property_get_bool("persist.bluetooth.bluetooth_audio_hal.enabled", false)) {
+        fileNames.push_back(AUDIO_POLICY_BLUETOOTH_HAL_ENABLED_XML_CONFIG_FILE_NAME);
     }
     fileNames.push_back(AUDIO_POLICY_XML_CONFIG_FILE_NAME);
 
diff --git a/services/mediaanalytics/Android.bp b/services/mediaanalytics/Android.bp
new file mode 100644
index 0000000..c93c120
--- /dev/null
+++ b/services/mediaanalytics/Android.bp
@@ -0,0 +1,49 @@
+// Media Statistics service
+//
+
+cc_binary {
+    name: "mediametrics",
+
+    srcs: [
+        "main_mediametrics.cpp",
+        "MediaAnalyticsService.cpp",
+    ],
+
+    shared_libs: [
+        "libcutils",
+        "liblog",
+        "libmedia",
+        "libutils",
+        "libbinder",
+        "libdl",
+        "libgui",
+        "libmedia",
+        "libmediautils",
+        "libmediametrics",
+        "libstagefright_foundation",
+        "libutils",
+    ],
+
+    static_libs: ["libregistermsext"],
+
+    include_dirs: [
+        "frameworks/av/media/libstagefright/include",
+        "frameworks/av/media/libstagefright/rtsp",
+        "frameworks/av/media/libstagefright/webm",
+        "frameworks/av/include/media",
+        "frameworks/av/include/camera",
+        "frameworks/native/include/media/openmax",
+        "frameworks/native/include/media/hardware",
+        "external/tremolo/Tremolo",
+    ],
+
+    init_rc: ["mediametrics.rc"],
+
+    cflags: [
+        "-Werror",
+        "-Wall",
+        "-Wno-error=deprecated-declarations",
+    ],
+    clang: true,
+
+}
diff --git a/services/mediaanalytics/Android.mk b/services/mediaanalytics/Android.mk
deleted file mode 100644
index 5b20e61..0000000
--- a/services/mediaanalytics/Android.mk
+++ /dev/null
@@ -1,47 +0,0 @@
-# Media Statistics service
-#
-LOCAL_PATH:= $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES:= \
-    main_mediametrics.cpp              \
-    MediaAnalyticsService.cpp
-
-LOCAL_SHARED_LIBRARIES := \
-    libcutils                   \
-    liblog                      \
-    libmedia                    \
-    libutils                    \
-    libbinder                   \
-    libdl                       \
-    libgui                      \
-    libmedia                    \
-    libmediautils               \
-    libmediametrics             \
-    libstagefright_foundation   \
-    libutils
-
-LOCAL_STATIC_LIBRARIES := \
-        libregistermsext
-
-LOCAL_C_INCLUDES :=                                                 \
-    $(TOP)/frameworks/av/media/libstagefright/include               \
-    $(TOP)/frameworks/av/media/libstagefright/rtsp                  \
-    $(TOP)/frameworks/av/media/libstagefright/wifi-display          \
-    $(TOP)/frameworks/av/media/libstagefright/webm                  \
-    $(TOP)/frameworks/av/include/media                              \
-    $(TOP)/frameworks/av/include/camera                             \
-    $(TOP)/frameworks/native/include/media/openmax                  \
-    $(TOP)/frameworks/native/include/media/hardware                 \
-    $(TOP)/external/tremolo/Tremolo
-
-
-LOCAL_MODULE:= mediametrics
-
-LOCAL_INIT_RC := mediametrics.rc
-
-LOCAL_CFLAGS := -Werror -Wall -Wno-error=deprecated-declarations
-LOCAL_CLANG := true
-
-include $(BUILD_EXECUTABLE)
diff --git a/services/mediacodec/seccomp_policy/mediacodec-arm.policy b/services/mediacodec/seccomp_policy/mediacodec-arm.policy
index 6ec8895..3870a11 100644
--- a/services/mediacodec/seccomp_policy/mediacodec-arm.policy
+++ b/services/mediacodec/seccomp_policy/mediacodec-arm.policy
@@ -13,6 +13,9 @@
 ppoll: 1
 mmap2: 1
 getrandom: 1
+memfd_create: 1
+ftruncate: 1
+ftruncate64: 1
 
 # mremap: Ensure |flags| are (MREMAP_MAYMOVE | MREMAP_FIXED) TODO: Once minijail
 # parser support for '<' is in this needs to be modified to also prevent
diff --git a/services/mediacodec/seccomp_policy/mediacodec-x86.policy b/services/mediacodec/seccomp_policy/mediacodec-x86.policy
index 821e69f..b4f5ee9 100644
--- a/services/mediacodec/seccomp_policy/mediacodec-x86.policy
+++ b/services/mediacodec/seccomp_policy/mediacodec-x86.policy
@@ -50,6 +50,9 @@
 nanosleep: 1
 sched_setscheduler: 1
 uname: 1
+memfd_create: 1
+ftruncate: 1
+ftruncate64: 1
 
 # Required by AddressSanitizer
 gettid: 1
diff --git a/services/mediaextractor/mediaextractor.rc b/services/mediaextractor/mediaextractor.rc
index 5fc2941..6b2d0a5 100644
--- a/services/mediaextractor/mediaextractor.rc
+++ b/services/mediaextractor/mediaextractor.rc
@@ -2,5 +2,7 @@
     class main
     user mediaex
     group drmrpc mediadrm
+    # TODO(b/123275379): Remove updatable when http://aosp/878198 has landed
+    updatable
     ioprio rt 4
     writepid /dev/cpuset/foreground/tasks
diff --git a/services/mediaresourcemanager/Android.bp b/services/mediaresourcemanager/Android.bp
new file mode 100644
index 0000000..1c63f64
--- /dev/null
+++ b/services/mediaresourcemanager/Android.bp
@@ -0,0 +1,28 @@
+
+
+cc_library_shared {
+    name: "libresourcemanagerservice",
+
+    srcs: [
+        "ResourceManagerService.cpp",
+        "ServiceLog.cpp",
+    ],
+
+    shared_libs: [
+        "libmedia",
+        "libmediautils",
+        "libbinder",
+        "libutils",
+        "liblog",
+    ],
+
+    compile_multilib: "32",
+
+    include_dirs: ["frameworks/av/include"],
+
+    cflags: [
+        "-Werror",
+        "-Wall",
+    ],
+
+}
diff --git a/services/mediaresourcemanager/Android.mk b/services/mediaresourcemanager/Android.mk
deleted file mode 100644
index 5823036..0000000
--- a/services/mediaresourcemanager/Android.mk
+++ /dev/null
@@ -1,20 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES := ResourceManagerService.cpp ServiceLog.cpp
-
-LOCAL_SHARED_LIBRARIES := libmedia libmediautils libbinder libutils liblog
-
-LOCAL_MODULE:= libresourcemanagerservice
-
-LOCAL_32_BIT_ONLY := true
-
-LOCAL_C_INCLUDES += \
-    frameworks/av/include
-
-LOCAL_CFLAGS += -Werror -Wall
-
-include $(BUILD_SHARED_LIBRARY)
-
-include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/services/mediaresourcemanager/test/Android.bp b/services/mediaresourcemanager/test/Android.bp
new file mode 100644
index 0000000..70e8833
--- /dev/null
+++ b/services/mediaresourcemanager/test/Android.bp
@@ -0,0 +1,41 @@
+// Build the unit tests.
+cc_test {
+    name: "ResourceManagerService_test",
+    srcs: ["ResourceManagerService_test.cpp"],
+    shared_libs: [
+        "libbinder",
+        "liblog",
+        "libmedia",
+        "libresourcemanagerservice",
+        "libutils",
+    ],
+    include_dirs: [
+        "frameworks/av/include",
+        "frameworks/av/services/mediaresourcemanager",
+    ],
+    cflags: [
+        "-Werror",
+        "-Wall",
+    ],
+    compile_multilib: "32",
+}
+
+cc_test {
+    name: "ServiceLog_test",
+    srcs: ["ServiceLog_test.cpp"],
+    shared_libs: [
+        "liblog",
+        "libmedia",
+        "libresourcemanagerservice",
+        "libutils",
+    ],
+    include_dirs: [
+        "frameworks/av/include",
+        "frameworks/av/services/mediaresourcemanager",
+    ],
+    cflags: [
+        "-Werror",
+        "-Wall",
+    ],
+    compile_multilib: "32",
+}
diff --git a/services/mediaresourcemanager/test/Android.mk b/services/mediaresourcemanager/test/Android.mk
deleted file mode 100644
index 6abcf92..0000000
--- a/services/mediaresourcemanager/test/Android.mk
+++ /dev/null
@@ -1,52 +0,0 @@
-# Build the unit tests.
-LOCAL_PATH:= $(call my-dir)
-include $(CLEAR_VARS)
-
-LOCAL_MODULE := ResourceManagerService_test
-
-LOCAL_MODULE_TAGS := tests
-
-LOCAL_SRC_FILES := \
-  ResourceManagerService_test.cpp \
-
-LOCAL_SHARED_LIBRARIES := \
-  libbinder \
-  liblog \
-  libmedia \
-  libresourcemanagerservice \
-  libutils \
-
-LOCAL_C_INCLUDES := \
-  frameworks/av/include \
-  frameworks/av/services/mediaresourcemanager \
-
-LOCAL_CFLAGS += -Werror -Wall
-
-LOCAL_32_BIT_ONLY := true
-
-include $(BUILD_NATIVE_TEST)
-
-include $(CLEAR_VARS)
-
-LOCAL_MODULE := ServiceLog_test
-
-LOCAL_MODULE_TAGS := tests
-
-LOCAL_SRC_FILES := \
-  ServiceLog_test.cpp \
-
-LOCAL_SHARED_LIBRARIES := \
-  liblog \
-  libmedia \
-  libresourcemanagerservice \
-  libutils \
-
-LOCAL_C_INCLUDES := \
-  frameworks/av/include \
-  frameworks/av/services/mediaresourcemanager \
-
-LOCAL_CFLAGS += -Werror -Wall
-
-LOCAL_32_BIT_ONLY := true
-
-include $(BUILD_NATIVE_TEST)