diff --git a/apex/Android.bp b/apex/Android.bp
index d198be0..aacb9a8 100644
--- a/apex/Android.bp
+++ b/apex/Android.bp
@@ -105,6 +105,8 @@
         "mediaswcodec",
     ],
     native_shared_libs: [
+        "libcodec2_hidl@1.0",
+        "libcodec2_hidl@1.1",
         "libstagefright_foundation",
     ],
     prebuilts: [
diff --git a/drm/libmediadrm/CryptoHal.cpp b/drm/libmediadrm/CryptoHal.cpp
index 9d39f83..af17679 100644
--- a/drm/libmediadrm/CryptoHal.cpp
+++ b/drm/libmediadrm/CryptoHal.cpp
@@ -146,6 +146,9 @@
                 plugin = hPlugin;
             }
         );
+    if (!hResult.isOk()) {
+        mInitCheck = DEAD_OBJECT;
+    }
     return plugin;
 }
 
@@ -179,10 +182,8 @@
         }
     }
 
-    if (mPlugin == NULL) {
-        mInitCheck = ERROR_UNSUPPORTED;
-    } else {
-        mInitCheck = OK;
+    if (mInitCheck == NO_INIT) {
+        mInitCheck = mPlugin == NULL ? ERROR_UNSUPPORTED : OK;
     }
 
     return mInitCheck;
diff --git a/drm/libmediadrm/interface/mediadrm/DrmUtils.h b/drm/libmediadrm/interface/mediadrm/DrmUtils.h
index 4a169ee..c362aa6 100644
--- a/drm/libmediadrm/interface/mediadrm/DrmUtils.h
+++ b/drm/libmediadrm/interface/mediadrm/DrmUtils.h
@@ -127,7 +127,7 @@
     ::V1_4::IDrmPlugin::getLogMessages_cb cb = [&](
             ::V1_4::Status status,
             hidl_vec<::V1_4::LogMessage> hLogs) {
-        if (::V1_4::Status::OK == status) {
+        if (::V1_4::Status::OK != status) {
             err = status;
             return;
         }
diff --git a/media/codec2/hidl/1.0/utils/Android.bp b/media/codec2/hidl/1.0/utils/Android.bp
index f38a688..008def8 100644
--- a/media/codec2/hidl/1.0/utils/Android.bp
+++ b/media/codec2/hidl/1.0/utils/Android.bp
@@ -89,6 +89,7 @@
         "libbase",
         "libcodec2",
         "libcodec2_vndk",
+        "libcodec2_hidl_plugin_stub",
         "libcutils",
         "libhidlbase",
         "liblog",
@@ -102,9 +103,17 @@
         vendor: {
             exclude_shared_libs: [
                 "libstagefright_bufferqueue_helper_novndk",
+                "libcodec2_hidl_plugin_stub",
             ],
             shared_libs: [
                 "libstagefright_bufferqueue_helper",
+                "libcodec2_hidl_plugin",
+            ],
+        },
+        apex: {
+            exclude_shared_libs: [
+                "libcodec2_hidl_plugin",
+                "libcodec2_hidl_plugin_stub",
             ],
         },
     },
diff --git a/media/codec2/hidl/1.0/utils/Component.cpp b/media/codec2/hidl/1.0/utils/Component.cpp
index 8a84601..082c5e3 100644
--- a/media/codec2/hidl/1.0/utils/Component.cpp
+++ b/media/codec2/hidl/1.0/utils/Component.cpp
@@ -22,6 +22,10 @@
 #include <codec2/hidl/1.0/ComponentStore.h>
 #include <codec2/hidl/1.0/InputBufferManager.h>
 
+#ifndef __ANDROID_APEX__
+#include <FilterWrapper.h>
+#endif
+
 #include <hidl/HidlBinderSupport.h>
 #include <utils/Timers.h>
 
@@ -390,10 +394,17 @@
         uint32_t allocatorId,
         createBlockPool_cb _hidl_cb) {
     std::shared_ptr<C2BlockPool> blockPool;
+#ifdef __ANDROID_APEX__
     c2_status_t status = CreateCodec2BlockPool(
             static_cast<C2PlatformAllocatorStore::id_t>(allocatorId),
             mComponent,
             &blockPool);
+#else
+    c2_status_t status = ComponentStore::GetFilterWrapper()->createBlockPool(
+            static_cast<C2PlatformAllocatorStore::id_t>(allocatorId),
+            mComponent,
+            &blockPool);
+#endif
     if (status != C2_OK) {
         blockPool = nullptr;
     }
diff --git a/media/codec2/hidl/1.0/utils/ComponentStore.cpp b/media/codec2/hidl/1.0/utils/ComponentStore.cpp
index 9b9d449..1c0d5b0 100644
--- a/media/codec2/hidl/1.0/utils/ComponentStore.cpp
+++ b/media/codec2/hidl/1.0/utils/ComponentStore.cpp
@@ -35,6 +35,14 @@
 #include <ostream>
 #include <sstream>
 
+#ifndef __ANDROID_APEX__
+#include <codec2/hidl/plugin/FilterPlugin.h>
+#include <dlfcn.h>
+#include <C2Config.h>
+#include <DefaultFilterPlugin.h>
+#include <FilterWrapper.h>
+#endif
+
 namespace android {
 namespace hardware {
 namespace media {
@@ -176,6 +184,16 @@
     return mParameterCache;
 }
 
+#ifndef __ANDROID_APEX__
+// static
+std::shared_ptr<FilterWrapper> ComponentStore::GetFilterWrapper() {
+    constexpr const char kPluginPath[] = "libc2filterplugin.so";
+    static std::shared_ptr<FilterWrapper> wrapper = FilterWrapper::Create(
+            std::make_unique<DefaultFilterPlugin>(kPluginPath));
+    return wrapper;
+}
+#endif
+
 // Methods from ::android::hardware::media::c2::V1_0::IComponentStore
 Return<void> ComponentStore::createComponent(
         const hidl_string& name,
@@ -189,6 +207,9 @@
             mStore->createComponent(name, &c2component));
 
     if (status == Status::OK) {
+#ifndef __ANDROID_APEX__
+        c2component = GetFilterWrapper()->maybeWrapComponent(c2component);
+#endif
         onInterfaceLoaded(c2component->intf());
         component = new Component(c2component, listener, this, pool);
         if (!component) {
@@ -214,8 +235,12 @@
         createInterface_cb _hidl_cb) {
     std::shared_ptr<C2ComponentInterface> c2interface;
     c2_status_t res = mStore->createInterface(name, &c2interface);
+
     sp<IComponentInterface> interface;
     if (res == C2_OK) {
+#ifndef __ANDROID_APEX__
+        c2interface = GetFilterWrapper()->maybeWrapInterface(c2interface);
+#endif
         onInterfaceLoaded(c2interface);
         interface = new ComponentInterface(c2interface, mParameterCache);
     }
@@ -458,7 +483,6 @@
     return Void();
 }
 
-
 }  // namespace utils
 }  // namespace V1_0
 }  // namespace c2
diff --git a/media/codec2/hidl/1.0/utils/include/codec2/hidl/1.0/ComponentStore.h b/media/codec2/hidl/1.0/utils/include/codec2/hidl/1.0/ComponentStore.h
index fe7d048..27e2a05 100644
--- a/media/codec2/hidl/1.0/utils/include/codec2/hidl/1.0/ComponentStore.h
+++ b/media/codec2/hidl/1.0/utils/include/codec2/hidl/1.0/ComponentStore.h
@@ -37,6 +37,8 @@
 #include <vector>
 
 namespace android {
+class FilterWrapper;
+
 namespace hardware {
 namespace media {
 namespace c2 {
@@ -74,6 +76,8 @@
      */
     std::shared_ptr<ParameterCache> getParameterCache() const;
 
+    static std::shared_ptr<FilterWrapper> GetFilterWrapper();
+
     // Methods from ::android::hardware::media::c2::V1_0::IComponentStore.
     virtual Return<void> createComponent(
             const hidl_string& name,
diff --git a/media/codec2/hidl/1.1/utils/Android.bp b/media/codec2/hidl/1.1/utils/Android.bp
index 1d34ce9..839a910 100644
--- a/media/codec2/hidl/1.1/utils/Android.bp
+++ b/media/codec2/hidl/1.1/utils/Android.bp
@@ -100,6 +100,7 @@
         "libbase",
         "libcodec2",
         "libcodec2_hidl@1.0",
+        "libcodec2_hidl_plugin_stub",
         "libcodec2_vndk",
         "libcutils",
         "libhidlbase",
@@ -114,9 +115,17 @@
         vendor: {
             exclude_shared_libs: [
                 "libstagefright_bufferqueue_helper_novndk",
+                "libcodec2_hidl_plugin_stub",
             ],
             shared_libs: [
                 "libstagefright_bufferqueue_helper",
+                "libcodec2_hidl_plugin",
+            ],
+        },
+        apex: {
+            exclude_shared_libs: [
+                "libcodec2_hidl_plugin_stub",
+                "libcodec2_hidl_plugin",
             ],
         },
     },
diff --git a/media/codec2/hidl/1.1/utils/Component.cpp b/media/codec2/hidl/1.1/utils/Component.cpp
index ed281e6..1d7d3d8 100644
--- a/media/codec2/hidl/1.1/utils/Component.cpp
+++ b/media/codec2/hidl/1.1/utils/Component.cpp
@@ -22,6 +22,10 @@
 #include <codec2/hidl/1.1/ComponentStore.h>
 #include <codec2/hidl/1.1/InputBufferManager.h>
 
+#ifndef __ANDROID_APEX__
+#include <FilterWrapper.h>
+#endif
+
 #include <hidl/HidlBinderSupport.h>
 #include <utils/Timers.h>
 
@@ -390,10 +394,17 @@
         uint32_t allocatorId,
         createBlockPool_cb _hidl_cb) {
     std::shared_ptr<C2BlockPool> blockPool;
+#ifdef __ANDROID_APEX__
     c2_status_t status = CreateCodec2BlockPool(
             static_cast<C2PlatformAllocatorStore::id_t>(allocatorId),
             mComponent,
             &blockPool);
+#else
+    c2_status_t status = ComponentStore::GetFilterWrapper()->createBlockPool(
+            static_cast<C2PlatformAllocatorStore::id_t>(allocatorId),
+            mComponent,
+            &blockPool);
+#endif
     if (status != C2_OK) {
         blockPool = nullptr;
     }
diff --git a/media/codec2/hidl/1.1/utils/ComponentStore.cpp b/media/codec2/hidl/1.1/utils/ComponentStore.cpp
index 225cd09..163686d 100644
--- a/media/codec2/hidl/1.1/utils/ComponentStore.cpp
+++ b/media/codec2/hidl/1.1/utils/ComponentStore.cpp
@@ -35,6 +35,14 @@
 #include <ostream>
 #include <sstream>
 
+#ifndef __ANDROID_APEX__
+#include <codec2/hidl/plugin/FilterPlugin.h>
+#include <dlfcn.h>
+#include <C2Config.h>
+#include <DefaultFilterPlugin.h>
+#include <FilterWrapper.h>
+#endif
+
 namespace android {
 namespace hardware {
 namespace media {
@@ -176,6 +184,16 @@
     return mParameterCache;
 }
 
+#ifndef __ANDROID_APEX__
+// static
+std::shared_ptr<FilterWrapper> ComponentStore::GetFilterWrapper() {
+    constexpr const char kPluginPath[] = "libc2filterplugin.so";
+    static std::shared_ptr<FilterWrapper> wrapper = FilterWrapper::Create(
+            std::make_unique<DefaultFilterPlugin>(kPluginPath));
+    return wrapper;
+}
+#endif
+
 // Methods from ::android::hardware::media::c2::V1_0::IComponentStore
 Return<void> ComponentStore::createComponent(
         const hidl_string& name,
@@ -189,6 +207,9 @@
             mStore->createComponent(name, &c2component));
 
     if (status == Status::OK) {
+#ifndef __ANDROID_APEX__
+        c2component = GetFilterWrapper()->maybeWrapComponent(c2component);
+#endif
         onInterfaceLoaded(c2component->intf());
         component = new Component(c2component, listener, this, pool);
         if (!component) {
@@ -216,6 +237,9 @@
     c2_status_t res = mStore->createInterface(name, &c2interface);
     sp<IComponentInterface> interface;
     if (res == C2_OK) {
+#ifndef __ANDROID_APEX__
+        c2interface = GetFilterWrapper()->maybeWrapInterface(c2interface);
+#endif
         onInterfaceLoaded(c2interface);
         interface = new ComponentInterface(c2interface, mParameterCache);
     }
diff --git a/media/codec2/hidl/1.1/utils/include/codec2/hidl/1.1/ComponentStore.h b/media/codec2/hidl/1.1/utils/include/codec2/hidl/1.1/ComponentStore.h
index 1f04391..f6daee7 100644
--- a/media/codec2/hidl/1.1/utils/include/codec2/hidl/1.1/ComponentStore.h
+++ b/media/codec2/hidl/1.1/utils/include/codec2/hidl/1.1/ComponentStore.h
@@ -38,6 +38,8 @@
 #include <vector>
 
 namespace android {
+class FilterWrapper;
+
 namespace hardware {
 namespace media {
 namespace c2 {
@@ -75,6 +77,8 @@
      */
     std::shared_ptr<ParameterCache> getParameterCache() const;
 
+    static std::shared_ptr<FilterWrapper> GetFilterWrapper();
+
     // Methods from ::android::hardware::media::c2::V1_0::IComponentStore.
     virtual Return<void> createComponent(
             const hidl_string& name,
diff --git a/media/codec2/hidl/plugin/Android.bp b/media/codec2/hidl/plugin/Android.bp
new file mode 100644
index 0000000..4708b12
--- /dev/null
+++ b/media/codec2/hidl/plugin/Android.bp
@@ -0,0 +1,66 @@
+cc_library_headers {
+    name: "libcodec2_hidl_plugin_headers",
+    vendor_available: true,
+    export_include_dirs: [
+        "include",
+    ],
+}
+
+cc_library {
+    name: "libcodec2_hidl_plugin_stub",
+
+    srcs: [
+        "DefaultFilterPlugin.cpp",
+        "FilterWrapperStub.cpp",
+    ],
+
+    header_libs: [
+        "libcodec2_internal", // private
+    ],
+
+    shared_libs: [
+        "libbase",
+        "libcodec2",
+        "libcodec2_vndk",
+        "liblog",
+        "libutils",
+    ],
+
+    export_include_dirs: [
+        "include",
+        "internal",
+    ],
+
+    apex_available: [
+        "//apex_available:platform",
+        "com.android.media.swcodec",
+    ],
+    min_sdk_version: "29",
+}
+
+cc_library {
+    name: "libcodec2_hidl_plugin",
+    vendor: true,
+
+    srcs: [
+        "DefaultFilterPlugin.cpp",
+        "FilterWrapper.cpp",
+    ],
+
+    header_libs: [
+        "libcodec2_internal", // private
+    ],
+
+    shared_libs: [
+        "libbase",
+        "libcodec2",
+        "libcodec2_vndk",
+        "liblog",
+        "libutils",
+    ],
+
+    export_include_dirs: [
+        "include",
+        "internal",
+    ],
+}
diff --git a/media/codec2/hidl/plugin/DefaultFilterPlugin.cpp b/media/codec2/hidl/plugin/DefaultFilterPlugin.cpp
new file mode 100644
index 0000000..cd1bcb0
--- /dev/null
+++ b/media/codec2/hidl/plugin/DefaultFilterPlugin.cpp
@@ -0,0 +1,108 @@
+/*
+ * Copyright 2020 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.
+ */
+
+//#define LOG_NDEBUG 0
+#define LOG_TAG "Codec2-DefaultFilterPlugin"
+#include <android-base/logging.h>
+
+#include <set>
+
+#include <dlfcn.h>
+
+#include <C2Config.h>
+#include <C2Debug.h>
+#include <C2ParamInternal.h>
+
+#include <codec2/hidl/plugin/FilterPlugin.h>
+
+#include <DefaultFilterPlugin.h>
+#include <FilterWrapper.h>
+
+namespace android {
+
+DefaultFilterPlugin::DefaultFilterPlugin(const char *pluginPath)
+    : mInit(NO_INIT),
+      mHandle(nullptr),
+      mDestroyPlugin(nullptr),
+      mPlugin(nullptr) {
+    mHandle = dlopen(pluginPath, RTLD_NOW | RTLD_NODELETE);
+    if (!mHandle) {
+        LOG(DEBUG) << "FilterPlugin: no plugin detected";
+        return;
+    }
+    GetFilterPluginVersionFunc getVersion =
+        (GetFilterPluginVersionFunc)dlsym(mHandle, "GetFilterPluginVersion");
+    if (!getVersion) {
+        LOG(WARNING) << "FilterPlugin: GetFilterPluginVersion undefined";
+        return;
+    }
+    int32_t version = getVersion();
+    if (version != FilterPlugin_V1::VERSION) {
+        LOG(WARNING) << "FilterPlugin: unrecognized version (" << version << ")";
+        return;
+    }
+    CreateFilterPluginFunc createPlugin =
+        (CreateFilterPluginFunc)dlsym(mHandle, "CreateFilterPlugin");
+    if (!createPlugin) {
+        LOG(WARNING) << "FilterPlugin: CreateFilterPlugin undefined";
+        return;
+    }
+    mDestroyPlugin =
+        (DestroyFilterPluginFunc)dlsym(mHandle, "DestroyFilterPlugin");
+    if (!mDestroyPlugin) {
+        LOG(WARNING) << "FilterPlugin: DestroyFilterPlugin undefined";
+        return;
+    }
+    mPlugin = (FilterPlugin_V1 *)createPlugin();
+    if (!mPlugin) {
+        LOG(WARNING) << "FilterPlugin: CreateFilterPlugin returned nullptr";
+        return;
+    }
+    mStore = mPlugin->getComponentStore();
+    if (!mStore) {
+        LOG(WARNING) << "FilterPlugin: FilterPlugin_V1::getComponentStore returned nullptr";
+        return;
+    }
+    mInit = OK;
+}
+
+DefaultFilterPlugin::~DefaultFilterPlugin() {
+    if (mHandle) {
+        if (mDestroyPlugin && mPlugin) {
+            mDestroyPlugin(mPlugin);
+            mPlugin = nullptr;
+        }
+        dlclose(mHandle);
+        mHandle = nullptr;
+        mDestroyPlugin = nullptr;
+    }
+}
+
+bool DefaultFilterPlugin::describe(C2String name, FilterWrapper::Descriptor *desc) {
+    if (mInit != OK) {
+        return false;
+    }
+    return mPlugin->describe(name, desc);
+}
+
+bool DefaultFilterPlugin::isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) {
+    if (mInit != OK) {
+        return false;
+    }
+    return mPlugin->isFilteringEnabled(intf);
+}
+
+}  // namespace android
diff --git a/media/codec2/hidl/plugin/FilterWrapper.cpp b/media/codec2/hidl/plugin/FilterWrapper.cpp
new file mode 100644
index 0000000..0b38bc1
--- /dev/null
+++ b/media/codec2/hidl/plugin/FilterWrapper.cpp
@@ -0,0 +1,921 @@
+/*
+ * Copyright 2020 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.
+ */
+
+//#define LOG_NDEBUG 0
+#define LOG_TAG "Codec2-FilterWrapper"
+#include <android-base/logging.h>
+
+#include <set>
+#include <sstream>
+
+#include <dlfcn.h>
+
+#include <C2Config.h>
+#include <C2Debug.h>
+#include <C2ParamInternal.h>
+
+#include <codec2/hidl/plugin/FilterPlugin.h>
+
+#include <FilterWrapper.h>
+
+namespace android {
+
+namespace {
+
+// Indices that the last filter in the chain should consume.
+static constexpr uint32_t kTypesForLastFilter[] = {
+    // In case we have an output surface, we want to use the block pool
+    // backed by the output surface for the output buffer going to the client.
+    C2PortBlockPoolsTuning::output::PARAM_TYPE,
+};
+
+class WrappedDecoderInterface : public C2ComponentInterface {
+public:
+    WrappedDecoderInterface(
+            std::shared_ptr<C2ComponentInterface> intf,
+            std::vector<FilterWrapper::Component> &&filters)
+        : mIntf(intf) {
+        takeFilters(std::move(filters));
+    }
+
+    ~WrappedDecoderInterface() override = default;
+
+    void takeFilters(std::vector<FilterWrapper::Component> &&filters) {
+        std::unique_lock lock(mMutex);
+        std::vector<std::unique_ptr<C2Param>> lastFilterParams;
+        if (!mFilters.empty()) {
+            std::vector<C2Param::Index> indices;
+            std::vector<std::shared_ptr<C2ParamDescriptor>> paramDescs;
+            c2_status_t err = mFilters.back().intf->querySupportedParams_nb(&paramDescs);
+            if (err != C2_OK) {
+                LOG(WARNING) << "WrappedDecoderInterface: " << mFilters.back().traits.name
+                        << " returned error for querySupportedParams_nb; err=" << err;
+                paramDescs.clear();
+            }
+            for (const std::shared_ptr<C2ParamDescriptor> &paramDesc : paramDescs) {
+                C2Param::Index index = paramDesc->index();
+                if (std::count(
+                            std::begin(kTypesForLastFilter),
+                            std::end(kTypesForLastFilter),
+                            index.type()) != 0) {
+                    if (index.forStream()) {
+                        // querySupportedParams does not return per-stream params.
+                        // We only support stream-0 for now.
+                        index = index.withStream(0u);
+                    }
+                    indices.push_back(index);
+                }
+            }
+            if (!indices.empty()) {
+                mFilters.back().intf->query_vb({}, indices, C2_MAY_BLOCK, &lastFilterParams);
+            }
+        }
+
+        // TODO: documentation
+        mFilters = std::move(filters);
+        mTypeToIndexForQuery.clear();
+        mTypeToIndexForConfig.clear();
+        for (size_t i = 0; i < mFilters.size(); ++i) {
+            if (i == 0) {
+                transferParams_l(mIntf, mFilters[0].intf, C2_MAY_BLOCK);
+            } else {
+                transferParams_l(mFilters[i - 1].intf, mFilters[i].intf, C2_MAY_BLOCK);
+            }
+            for (C2Param::Type type : mFilters[i].desc.controlParams) {
+                mTypeToIndexForQuery[type.type()] = i;
+                mTypeToIndexForConfig[type.type() & ~C2Param::CoreIndex::IS_REQUEST_FLAG] = i;
+            }
+            for (C2Param::Type type : mFilters[i].desc.affectedParams) {
+                mTypeToIndexForQuery[type.type()] = i;
+            }
+        }
+        if (!mFilters.empty()) {
+            for (uint32_t type : kTypesForLastFilter) {
+                mTypeToIndexForQuery[type] = mFilters.size() - 1;
+                mTypeToIndexForConfig[type & ~C2Param::CoreIndex::IS_REQUEST_FLAG] =
+                    mFilters.size() - 1;
+            }
+            if (!lastFilterParams.empty()) {
+                std::vector<C2Param *> paramPtrs(lastFilterParams.size());
+                std::transform(
+                        lastFilterParams.begin(),
+                        lastFilterParams.end(),
+                        paramPtrs.begin(),
+                        [](const std::unique_ptr<C2Param> &param) {
+                            return param.get();
+                        });
+                std::vector<std::unique_ptr<C2SettingResult>> failures;
+                mFilters.back().intf->config_vb(paramPtrs, C2_MAY_BLOCK, &failures);
+            }
+        }
+    }
+
+    C2String getName() const override { return mIntf->getName(); }
+
+    c2_node_id_t getId() const override { return mIntf->getId(); }
+
+    c2_status_t query_vb(
+            const std::vector<C2Param *> &stackParams,
+            const std::vector<C2Param::Index> &heapParamIndices,
+            c2_blocking_t mayBlock,
+            std::vector<std::unique_ptr<C2Param>>* const heapParams) const override {
+        std::unique_lock lock(mMutex);
+        std::list<C2Param *> stackParamsList(stackParams.size());
+        std::copy_n(stackParams.begin(), stackParams.size(), stackParamsList.begin());
+        heapParams->clear();
+        c2_status_t result = C2_OK;
+        // TODO: loop optimization
+        for (size_t i = 0; i < mFilters.size(); ++i) {
+            // Filter stack params according to mTypeToIndexForQuery
+            std::vector<C2Param *> stackParamsForFilter;
+            for (auto it = stackParamsList.begin(); it != stackParamsList.end(); ) {
+                C2Param *param = *it;
+                uint32_t type = param->type().type();
+                auto it2 = mTypeToIndexForQuery.find(type);
+                if (it2 == mTypeToIndexForQuery.end() || it2->second != i) {
+                    ++it;
+                    continue;
+                }
+                stackParamsForFilter.push_back(param);
+                it = stackParamsList.erase(it);
+            }
+            // Filter heap params according to mTypeToIndexForQuery
+            std::vector<C2Param::Index> heapParamIndicesForFilter;
+            for (size_t j = 0; j < heapParamIndices.size(); ++j) {
+                uint32_t type = heapParamIndices[j].type();
+                auto it = mTypeToIndexForQuery.find(type);
+                if (it == mTypeToIndexForQuery.end() || it->second != i) {
+                    continue;
+                }
+                heapParamIndicesForFilter.push_back(heapParamIndices[j]);
+            }
+            std::vector<std::unique_ptr<C2Param>> heapParamsForFilter;
+            const std::shared_ptr<C2ComponentInterface> &filter = mFilters[i].intf;
+            c2_status_t err = filter->query_vb(
+                    stackParamsForFilter, heapParamIndicesForFilter, mayBlock,
+                    &heapParamsForFilter);
+            if (err != C2_OK && err != C2_BAD_INDEX) {
+                LOG(WARNING) << "WrappedDecoderInterface: " << filter->getName()
+                        << " returned error for query_vb; err=" << err;
+                result = err;
+                continue;
+            }
+            heapParams->insert(
+                    heapParams->end(),
+                    std::make_move_iterator(heapParamsForFilter.begin()),
+                    std::make_move_iterator(heapParamsForFilter.end()));
+        }
+
+        std::vector<C2Param *> stackParamsForIntf;
+        std::copy_n(stackParamsList.begin(), stackParamsList.size(), stackParamsForIntf.begin());
+
+        // Gather heap params that did not get queried from the filter interfaces above.
+        // These need to be queried from the decoder interface.
+        std::vector<C2Param::Index> heapParamIndicesForIntf;
+        for (size_t j = 0; j < heapParamIndices.size(); ++j) {
+            uint32_t type = heapParamIndices[j].type();
+            if (mTypeToIndexForQuery.find(type) != mTypeToIndexForQuery.end()) {
+                continue;
+            }
+            heapParamIndicesForIntf.push_back(heapParamIndices[j]);
+        }
+
+        std::vector<std::unique_ptr<C2Param>> heapParamsForIntf;
+        c2_status_t err = mIntf->query_vb(
+                stackParamsForIntf, heapParamIndicesForIntf, mayBlock, &heapParamsForIntf);
+        if (err != C2_OK) {
+            LOG(err == C2_BAD_INDEX ? VERBOSE : WARNING)
+                    << "WrappedDecoderInterface: " << mIntf->getName()
+                    << " returned error for query_vb; err=" << err;
+            result = err;
+        }
+
+        // TODO: params needs to preserve the order
+        heapParams->insert(
+                heapParams->end(),
+                std::make_move_iterator(heapParamsForIntf.begin()),
+                std::make_move_iterator(heapParamsForIntf.end()));
+
+        return result;
+    }
+
+    c2_status_t config_vb(
+            const std::vector<C2Param *> &params,
+            c2_blocking_t mayBlock,
+            std::vector<std::unique_ptr<C2SettingResult>>* const failures) override {
+        std::unique_lock lock(mMutex);
+        c2_status_t result = C2_OK;
+        std::vector<C2Param *> paramsForIntf;
+        for (C2Param* param : params) {
+            auto it = mTypeToIndexForConfig.find(param->type().type());
+            if (it != mTypeToIndexForConfig.end()) {
+                continue;
+            }
+            paramsForIntf.push_back(param);
+        }
+        c2_status_t err = mIntf->config_vb(paramsForIntf, mayBlock, failures);
+        if (err != C2_OK) {
+            LOG(err == C2_BAD_INDEX ? VERBOSE : WARNING)
+                    << "WrappedDecoderInterface: " << mIntf->getName()
+                    << " returned error for config_vb; err=" << err;
+            result = err;
+        }
+        for (size_t i = 0; i < mFilters.size(); ++i) {
+            if (i == 0) {
+                transferParams_l(mIntf, mFilters[0].intf, mayBlock);
+            } else {
+                transferParams_l(mFilters[i - 1].intf, mFilters[i].intf, mayBlock);
+            }
+            const std::shared_ptr<C2ComponentInterface> &filter = mFilters[i].intf;
+            std::vector<std::unique_ptr<C2SettingResult>> filterFailures;
+            std::vector<C2Param *> paramsForFilter;
+            for (C2Param* param : params) {
+                auto it = mTypeToIndexForConfig.find(param->type().type());
+                if (it != mTypeToIndexForConfig.end() && it->second != i) {
+                    continue;
+                }
+                paramsForFilter.push_back(param);
+            }
+            c2_status_t err = filter->config_vb(paramsForFilter, mayBlock, &filterFailures);
+            if (err != C2_OK) {
+                LOG(err == C2_BAD_INDEX ? VERBOSE : WARNING)
+                        << "WrappedDecoderInterface: " << filter->getName()
+                        << " returned error for config_vb; err=" << err;
+                result = err;
+            }
+        }
+
+        return result;
+    }
+
+    c2_status_t createTunnel_sm(c2_node_id_t) override { return C2_OMITTED; }
+    c2_status_t releaseTunnel_sm(c2_node_id_t) override { return C2_OMITTED; }
+
+    c2_status_t querySupportedParams_nb(
+            std::vector<std::shared_ptr<C2ParamDescriptor>> * const params) const override {
+        std::unique_lock lock(mMutex);
+        c2_status_t result = mIntf->querySupportedParams_nb(params);
+        if (result != C2_OK) {
+            LOG(WARNING) << "WrappedDecoderInterface: " << mIntf->getName()
+                    << " returned error for querySupportedParams_nb; err=" << result;
+            return result;
+        }
+        // TODO: optimization idea --- pre-compute at takeFilter().
+        for (const FilterWrapper::Component &filter : mFilters) {
+            std::vector<std::shared_ptr<C2ParamDescriptor>> filterParams;
+            c2_status_t err = filter.intf->querySupportedParams_nb(&filterParams);
+            if (err != C2_OK) {
+                LOG(WARNING) << "WrappedDecoderInterface: " << filter.intf->getName()
+                        << " returned error for querySupportedParams_nb; err=" << result;
+                result = err;
+                continue;
+            }
+            for (const std::shared_ptr<C2ParamDescriptor> &paramDesc : filterParams) {
+                if (std::count(
+                        filter.desc.controlParams.begin(),
+                        filter.desc.controlParams.end(),
+                        paramDesc->index().type()) == 0) {
+                    continue;
+                }
+                params->push_back(paramDesc);
+            }
+        }
+        return result;
+    }
+
+    c2_status_t querySupportedValues_vb(
+            std::vector<C2FieldSupportedValuesQuery> &fields,
+            c2_blocking_t mayBlock) const override {
+        std::unique_lock lock(mMutex);
+        c2_status_t result = mIntf->querySupportedValues_vb(fields, mayBlock);
+        if (result != C2_OK && result != C2_BAD_INDEX) {
+            LOG(WARNING) << "WrappedDecoderInterface: " << mIntf->getName()
+                    << " returned error for querySupportedParams_nb; err=" << result;
+            return result;
+        }
+        for (const FilterWrapper::Component &filter : mFilters) {
+            std::vector<C2FieldSupportedValuesQuery> filterFields;
+            std::vector<size_t> indices;
+            for (size_t i = 0; i < fields.size(); ++i) {
+                const C2FieldSupportedValuesQuery &field = fields[i];
+                uint32_t type = C2Param::Index(_C2ParamInspector::GetIndex(field.field())).type();
+                if (std::count(
+                        filter.desc.controlParams.begin(),
+                        filter.desc.controlParams.end(),
+                        type) == 0) {
+                    continue;
+                }
+                filterFields.push_back(field);
+                indices.push_back(i);
+            }
+            c2_status_t err = filter.intf->querySupportedValues_vb(filterFields, mayBlock);
+            if (err != C2_OK && err != C2_BAD_INDEX) {
+                LOG(WARNING) << "WrappedDecoderInterface: " << filter.intf->getName()
+                        << " returned error for querySupportedParams_nb; err=" << result;
+                result = err;
+                continue;
+            }
+            for (size_t i = 0; i < filterFields.size(); ++i) {
+                fields[indices[i]] = filterFields[i];
+            }
+        }
+        return result;
+    }
+
+private:
+    mutable std::mutex mMutex;
+    std::shared_ptr<C2ComponentInterface> mIntf;
+    std::vector<FilterWrapper::Component> mFilters;
+    std::map<uint32_t, size_t> mTypeToIndexForQuery;
+    std::map<uint32_t, size_t> mTypeToIndexForConfig;
+
+    c2_status_t transferParams_l(
+            const std::shared_ptr<C2ComponentInterface> &curr,
+            const std::shared_ptr<C2ComponentInterface> &next,
+            c2_blocking_t mayBlock) {
+        // NOTE: this implementation is preliminary --- it could change once
+        // we define what parameters needs to be propagated in component chaining.
+        std::vector<std::shared_ptr<C2ParamDescriptor>> paramDescs;
+        c2_status_t err = next->querySupportedParams_nb(&paramDescs);
+        if (err != C2_OK) {
+            LOG(DEBUG) << "WrappedDecoderInterface: " << next->getName()
+                    << " returned error for querySupportedParams_nb; err=" << err;
+            return err;
+        }
+        // Find supported input params from the next interface and flip direction
+        // so they become output params.
+        std::vector<C2Param::Index> indices;
+        for (const std::shared_ptr<C2ParamDescriptor> &paramDesc : paramDescs) {
+            C2Param::Index index = paramDesc->index();
+            if (!index.forInput() || paramDesc->isReadOnly()) {
+                continue;
+            }
+            if (index.forStream()) {
+                uint32_t stream = index.stream();
+                index = index.withPort(true /* output */).withStream(stream);
+            } else {
+                index = index.withPort(true /* output */);
+            }
+            indices.push_back(index);
+        }
+        // Query those output params from the current interface
+        std::vector<std::unique_ptr<C2Param>> heapParams;
+        err = curr->query_vb({}, indices, mayBlock, &heapParams);
+        if (err != C2_OK && err != C2_BAD_INDEX) {
+            LOG(DEBUG) << "WrappedDecoderInterface: " << curr->getName()
+                    << " returned error for query_vb; err=" << err;
+            return err;
+        }
+        // Flip the direction of the queried params, so they become input parameters.
+        // Configure the next interface with the params.
+        std::vector<C2Param *> configParams;
+        for (size_t i = 0; i < heapParams.size(); ++i) {
+            if (heapParams[i]->forStream()) {
+                heapParams[i] = C2Param::CopyAsStream(
+                        *heapParams[i], false /* output */, heapParams[i]->stream());
+            } else {
+                heapParams[i] = C2Param::CopyAsPort(*heapParams[i], false /* output */);
+            }
+            configParams.push_back(heapParams[i].get());
+        }
+        std::vector<std::unique_ptr<C2SettingResult>> failures;
+        err = next->config_vb(configParams, mayBlock, &failures);
+        if (err != C2_OK && err != C2_BAD_INDEX) {
+            LOG(DEBUG) << "WrappedDecoderInterface: " << next->getName()
+                    << " returned error for config_vb; err=" << err;
+            return err;
+        }
+        return C2_OK;
+    }
+};
+
+class WrappedDecoder : public C2Component, public std::enable_shared_from_this<WrappedDecoder> {
+public:
+    WrappedDecoder(
+            std::shared_ptr<C2Component> comp,
+            std::vector<FilterWrapper::Component> &&filters,
+            std::weak_ptr<FilterWrapper> filterWrapper)
+        : mComp(comp), mFilters(std::move(filters)), mFilterWrapper(filterWrapper) {
+        std::vector<FilterWrapper::Component> filtersDup(mFilters);
+        mIntf = std::make_shared<WrappedDecoderInterface>(
+                comp->intf(), std::move(filtersDup));
+    }
+
+    ~WrappedDecoder() override = default;
+
+    std::shared_ptr<C2ComponentInterface> intf() override { return mIntf; }
+
+    c2_status_t setListener_vb(
+            const std::shared_ptr<Listener> &listener, c2_blocking_t mayBlock) override {
+        if (listener) {
+            setListenerInternal(mFilters, listener, mayBlock);
+        } else {
+            mComp->setListener_vb(nullptr, mayBlock);
+            for (FilterWrapper::Component &filter : mFilters) {
+                filter.comp->setListener_vb(nullptr, mayBlock);
+            }
+        }
+        mListener = listener;
+        return C2_OK;
+    }
+
+    c2_status_t queue_nb(std::list<std::unique_ptr<C2Work>>* const items) override {
+        return mComp->queue_nb(items);
+    }
+
+    c2_status_t announce_nb(const std::vector<C2WorkOutline> &) override {
+        return C2_OMITTED;
+    }
+
+    c2_status_t flush_sm(
+            flush_mode_t mode, std::list<std::unique_ptr<C2Work>>* const flushedWork) override {
+        c2_status_t result = mComp->flush_sm(mode, flushedWork);
+        std::list<std::unique_ptr<C2Work>> filterFlushedWork;
+        for (FilterWrapper::Component filter : mRunningFilters) {
+            c2_status_t err = filter.comp->flush_sm(mode, &filterFlushedWork);
+            if (err != C2_OK) {
+                result = err;
+            }
+            flushedWork->splice(flushedWork->end(), filterFlushedWork);
+        }
+        return result;
+    }
+
+    c2_status_t drain_nb(drain_mode_t mode) override {
+        // TODO: simplify using comp->drain_nb(mode)
+        switch (mode) {
+        case DRAIN_COMPONENT_WITH_EOS: {
+            std::unique_ptr<C2Work> eosWork{new C2Work};
+            eosWork->input.flags = C2FrameData::FLAG_END_OF_STREAM;
+            eosWork->worklets.push_back(std::make_unique<C2Worklet>());
+            std::list<std::unique_ptr<C2Work>> items;
+            items.push_back(std::move(eosWork));
+            mComp->queue_nb(&items);
+            return C2_OK;
+        }
+        case DRAIN_COMPONENT_NO_EOS:
+        case DRAIN_CHAIN:
+        default:
+            return C2_BAD_VALUE;
+        }
+    }
+
+    c2_status_t start() override {
+        std::vector<FilterWrapper::Component> filters;
+        if (std::shared_ptr<FilterWrapper> filterWrapper = mFilterWrapper.lock()) {
+            // Let's check if we have filters that we can skip
+            for (FilterWrapper::Component &filter : mFilters) {
+                if (!filterWrapper->isFilteringEnabled(filter.intf)) {
+                    LOG(VERBOSE) << "filtering disabled for " << filter.traits.name;
+                    continue;
+                }
+                LOG(VERBOSE) << "filtering enabled for " << filter.traits.name;
+                filters.push_back(filter);
+            }
+            if (filters.size() < mFilters.size()) {
+                LOG(VERBOSE) << (mFilters.size() - filters.size()) << " filter(s) skipped";
+                setListenerInternal(filters, mListener, C2_MAY_BLOCK);
+                std::vector filtersCopy(filters);
+                mIntf->takeFilters(std::move(filtersCopy));
+            }
+        }
+
+        c2_status_t err = mComp->start();
+        if (err != C2_OK) {
+            return err;
+        }
+        for (FilterWrapper::Component &filter : filters) {
+            c2_status_t err = filter.comp->start();
+            if (err != C2_OK) {
+                // Previous components are already started successfully;
+                // we ended up in an incoherent state.
+                return C2_CORRUPTED;
+            }
+        }
+        mRunningFilters = std::move(filters);
+        return C2_OK;
+    }
+
+    c2_status_t stop() override {
+        c2_status_t err = mComp->stop();
+        if (err != C2_OK) {
+            return err;
+        }
+        for (FilterWrapper::Component filter : mRunningFilters) {
+            c2_status_t err = filter.comp->stop();
+            if (err != C2_OK) {
+                // Previous components are already stopped successfully;
+                // we ended up in an incoherent state.
+                return C2_CORRUPTED;
+            }
+        }
+        mRunningFilters.clear();
+        return C2_OK;
+    }
+
+    c2_status_t reset() override {
+        c2_status_t result = mComp->reset();
+        if (result != C2_OK) {
+            result = C2_CORRUPTED;
+        }
+        for (FilterWrapper::Component filter : mFilters) {
+            c2_status_t err = filter.comp->reset();
+            if (err != C2_OK) {
+                // Previous components are already reset successfully;
+                // we ended up in an incoherent state.
+                result = C2_CORRUPTED;
+                // continue for the rest of the chain
+            }
+        }
+        mRunningFilters.clear();
+        return result;
+    }
+
+    c2_status_t release() override {
+        c2_status_t result = mComp->release();
+        if (result != C2_OK) {
+            result = C2_CORRUPTED;
+        }
+        for (FilterWrapper::Component filter : mFilters) {
+            c2_status_t err = filter.comp->release();
+            if (err != C2_OK) {
+                // Previous components are already released successfully;
+                // we ended up in an incoherent state.
+                result = C2_CORRUPTED;
+                // continue for the rest of the chain
+            }
+        }
+        mRunningFilters.clear();
+        return result;
+    }
+
+private:
+    class PassingListener : public Listener {
+    public:
+        PassingListener(
+                std::shared_ptr<C2Component> wrappedComponent,
+                const std::shared_ptr<Listener> &wrappedComponentListener,
+                std::shared_ptr<C2Component> nextComponent)
+            : mWrappedComponent(wrappedComponent),
+              mWrappedComponentListener(wrappedComponentListener),
+              mNextComponent(nextComponent) {
+        }
+
+        void onWorkDone_nb(
+                std::weak_ptr<C2Component>,
+                std::list<std::unique_ptr<C2Work>> workItems) override {
+            std::shared_ptr<C2Component> nextComponent = mNextComponent.lock();
+            std::list<std::unique_ptr<C2Work>> failedWorkItems;
+            if (!nextComponent) {
+                for (std::unique_ptr<C2Work> &work : workItems) {
+                    // Next component unexpectedly released while the work is
+                    // in-flight. Report C2_CORRUPTED to the client.
+                    work->result = C2_CORRUPTED;
+                    failedWorkItems.push_back(std::move(work));
+                }
+                workItems.clear();
+            } else {
+                for (auto it = workItems.begin(); it != workItems.end(); ) {
+                    const std::unique_ptr<C2Work> &work = *it;
+                    if (work->result != C2_OK
+                            || work->worklets.size() != 1) {
+                        failedWorkItems.push_back(std::move(*it));
+                        it = workItems.erase(it);
+                        continue;
+                    }
+                    C2FrameData &output = work->worklets.front()->output;
+                    c2_cntr64_t customOrdinal = work->input.ordinal.customOrdinal;
+                    work->input = std::move(output);
+                    work->input.ordinal.customOrdinal = customOrdinal;
+                    output.flags = C2FrameData::flags_t(0);
+                    output.buffers.clear();
+                    output.configUpdate.clear();
+                    output.infoBuffers.clear();
+                    ++it;
+                }
+            }
+            if (!failedWorkItems.empty()) {
+                for (const std::unique_ptr<C2Work> &work : failedWorkItems) {
+                    LOG(VERBOSE) << "work #" << work->input.ordinal.frameIndex.peek()
+                            << " failed: err=" << work->result
+                            << " worklets.size()=" << work->worklets.size();
+                }
+                if (std::shared_ptr<Listener> wrappedComponentListener =
+                        mWrappedComponentListener.lock()) {
+                    wrappedComponentListener->onWorkDone_nb(
+                            mWrappedComponent, std::move(failedWorkItems));
+                }
+            }
+            if (!workItems.empty()) {
+                nextComponent->queue_nb(&workItems);
+            }
+        }
+
+        void onTripped_nb(
+                std::weak_ptr<C2Component>,
+                std::vector<std::shared_ptr<C2SettingResult>>) override {
+            // Trip not supported
+        }
+
+        void onError_nb(std::weak_ptr<C2Component>, uint32_t errorCode) {
+            if (std::shared_ptr<Listener> wrappedComponentListener =
+                    mWrappedComponentListener.lock()) {
+                wrappedComponentListener->onError_nb(mWrappedComponent, errorCode);
+            }
+        }
+
+    private:
+        std::weak_ptr<C2Component> mWrappedComponent;
+        std::weak_ptr<Listener> mWrappedComponentListener;
+        std::weak_ptr<C2Component> mNextComponent;
+    };
+
+    class LastListener : public Listener {
+    public:
+        LastListener(
+                std::shared_ptr<C2Component> wrappedComponent,
+                const std::shared_ptr<Listener> &wrappedComponentListener)
+            : mWrappedComponent(wrappedComponent),
+              mWrappedComponentListener(wrappedComponentListener) {
+        }
+
+        void onWorkDone_nb(
+                std::weak_ptr<C2Component>,
+                std::list<std::unique_ptr<C2Work>> workItems) override {
+            if (mWrappedComponent.expired()) {
+                return;
+            }
+            if (std::shared_ptr<Listener> wrappedComponentListener =
+                    mWrappedComponentListener.lock()) {
+                wrappedComponentListener->onWorkDone_nb(
+                        mWrappedComponent, std::move(workItems));
+            }
+        }
+
+        void onTripped_nb(
+                std::weak_ptr<C2Component>,
+                std::vector<std::shared_ptr<C2SettingResult>>) override {
+            // Trip not supported
+        }
+
+        void onError_nb(std::weak_ptr<C2Component>, uint32_t errorCode) {
+            if (mWrappedComponent.expired()) {
+                return;
+            }
+            if (std::shared_ptr<Listener> wrappedComponentListener =
+                    mWrappedComponentListener.lock()) {
+                wrappedComponentListener->onError_nb(mWrappedComponent, errorCode);
+            }
+        }
+
+    private:
+        std::weak_ptr<C2Component> mWrappedComponent;
+        std::weak_ptr<Listener> mWrappedComponentListener;
+    };
+
+    std::shared_ptr<C2Component> mComp;
+    std::shared_ptr<WrappedDecoderInterface> mIntf;
+    std::vector<FilterWrapper::Component> mFilters;
+    std::vector<FilterWrapper::Component> mRunningFilters;
+    std::weak_ptr<FilterWrapper> mFilterWrapper;
+    std::shared_ptr<Listener> mListener;
+#if defined(LOG_NDEBUG) && !LOG_NDEBUG
+    base::ScopedLogSeverity mScopedLogSeverity{base::VERBOSE};
+#endif
+
+    c2_status_t setListenerInternal(
+            const std::vector<FilterWrapper::Component> &filters,
+            const std::shared_ptr<Listener> &listener,
+            c2_blocking_t mayBlock) {
+        if (filters.empty()) {
+            return mComp->setListener_vb(listener, mayBlock);
+        }
+        std::shared_ptr passingListener = std::make_shared<PassingListener>(
+                shared_from_this(),
+                listener,
+                filters.front().comp);
+        mComp->setListener_vb(passingListener, mayBlock);
+        for (size_t i = 0; i < filters.size() - 1; ++i) {
+            filters[i].comp->setListener_vb(
+                    std::make_shared<PassingListener>(
+                            shared_from_this(),
+                            listener,
+                            filters[i + 1].comp),
+                    mayBlock);
+        }
+        filters.back().comp->setListener_vb(
+                std::make_shared<LastListener>(shared_from_this(), listener), mayBlock);
+        return C2_OK;
+    }
+};
+
+}  // anonymous namespace
+
+FilterWrapper::FilterWrapper(std::unique_ptr<Plugin> &&plugin)
+    : mInit(NO_INIT),
+      mPlugin(std::move(plugin)) {
+    if (mPlugin->status() != OK) {
+        LOG(ERROR) << "plugin not OK: " << mPlugin->status();
+        mPlugin.reset();
+        return;
+    }
+    mStore = mPlugin->getStore();
+    if (!mStore) {
+        LOG(ERROR) << "no store";
+        mPlugin.reset();
+        return;
+    }
+    std::vector<std::shared_ptr<const C2Component::Traits>> traits =
+        mStore->listComponents();
+    std::sort(
+            traits.begin(),
+            traits.end(),
+            [](std::shared_ptr<const C2Component::Traits> &a,
+                    std::shared_ptr<const C2Component::Traits> &b) {
+                return a->rank < b->rank;
+            });
+    for (size_t i = 0; i < traits.size(); ++i) {
+        const std::shared_ptr<const C2Component::Traits> &trait = traits[i];
+        if (trait->domain == C2Component::DOMAIN_OTHER
+                || trait->domain == C2Component::DOMAIN_AUDIO
+                || trait->kind != C2Component::KIND_OTHER) {
+            LOG(DEBUG) << trait->name << " is ignored because of domain/kind: "
+                << trait->domain << "/" << trait->kind;
+            continue;
+        }
+        Descriptor desc;
+        if (!mPlugin->describe(trait->name, &desc)) {
+            LOG(DEBUG) << trait->name << " is ignored because describe() failed";
+            continue;
+        }
+        mComponents.push_back({nullptr, nullptr, *trait, desc});
+    }
+    if (mComponents.empty()) {
+        LOG(DEBUG) << "FilterWrapper: no filter component found";
+        mPlugin.reset();
+        return;
+    }
+    mInit = OK;
+}
+
+FilterWrapper::~FilterWrapper() {
+}
+
+std::vector<FilterWrapper::Component> FilterWrapper::createFilters() {
+    std::vector<FilterWrapper::Component> filters;
+    for (const FilterWrapper::Component &filter : mComponents) {
+        std::shared_ptr<C2Component> comp;
+        std::shared_ptr<C2ComponentInterface> intf;
+        if (C2_OK != mStore->createComponent(filter.traits.name, &comp)) {
+            return {};
+        }
+        if (C2_OK != mStore->createInterface(filter.traits.name, &intf)) {
+            return {};
+        }
+        filters.push_back({comp, intf, filter.traits, filter.desc});
+    }
+    return filters;
+}
+
+C2Component::Traits FilterWrapper::getTraits(
+        const std::shared_ptr<C2ComponentInterface> &intf) {
+    {
+        std::unique_lock lock(mCacheMutex);
+        if (mCachedTraits.count(intf->getName())) {
+            return mCachedTraits.at(intf->getName());
+        }
+    }
+    C2ComponentDomainSetting domain;
+    C2ComponentKindSetting kind;
+    c2_status_t err = intf->query_vb({&domain, &kind}, {}, C2_MAY_BLOCK, nullptr);
+    C2Component::Traits traits = {
+        "query failed",  // name
+        C2Component::DOMAIN_OTHER,
+        C2Component::KIND_OTHER,
+        0,   // rank, unused
+        "",  // media type, unused
+        "",  // owner, unused
+        {},  // aliases, unused
+    };
+    if (err == C2_OK) {
+        traits = {
+            intf->getName(),
+            domain.value,
+            kind.value,
+            0,   // rank, unused
+            "",  // media type, unused
+            "",  // owner, unused
+            {},  // aliases, unused
+        };
+        std::unique_lock lock(mCacheMutex);
+        mCachedTraits[traits.name] = traits;
+    }
+    return traits;
+}
+
+std::shared_ptr<C2ComponentInterface> FilterWrapper::maybeWrapInterface(
+        const std::shared_ptr<C2ComponentInterface> intf) {
+    if (mInit != OK) {
+        LOG(VERBOSE) << "maybeWrapInterface: Wrapper not initialized: "
+                << intf->getName() << " is not wrapped.";
+        return intf;
+    }
+    C2Component::Traits traits = getTraits(intf);
+    if (traits.name != intf->getName()) {
+        LOG(INFO) << "maybeWrapInterface: Querying traits from " << intf->getName()
+                << " failed; not wrapping the interface";
+        return intf;
+    }
+    if ((traits.domain != C2Component::DOMAIN_VIDEO && traits.domain != C2Component::DOMAIN_IMAGE)
+            || traits.kind != C2Component::KIND_DECODER) {
+        LOG(VERBOSE) << "maybeWrapInterface: " << traits.name
+                << " is not video/image decoder; not wrapping the interface";
+        return intf;
+    }
+    return std::make_shared<WrappedDecoderInterface>(intf, createFilters());
+}
+
+std::shared_ptr<C2Component> FilterWrapper::maybeWrapComponent(
+        const std::shared_ptr<C2Component> comp) {
+    if (mInit != OK) {
+        LOG(VERBOSE) << "maybeWrapComponent: Wrapper not initialized: "
+                << comp->intf()->getName() << " is not wrapped.";
+        return comp;
+    }
+    C2Component::Traits traits = getTraits(comp->intf());
+    if (traits.name != comp->intf()->getName()) {
+        LOG(INFO) << "maybeWrapComponent: Querying traits from " << comp->intf()->getName()
+                << " failed; not wrapping the component";
+        return comp;
+    }
+    if ((traits.domain != C2Component::DOMAIN_VIDEO && traits.domain != C2Component::DOMAIN_IMAGE)
+            || traits.kind != C2Component::KIND_DECODER) {
+        LOG(VERBOSE) << "maybeWrapComponent: " << traits.name
+                << " is not video/image decoder; not wrapping the component";
+        return comp;
+    }
+    std::vector<Component> filters = createFilters();
+    std::shared_ptr wrapped = std::make_shared<WrappedDecoder>(
+            comp, std::move(filters), weak_from_this());
+    {
+        std::unique_lock lock(mWrappedComponentsMutex);
+        std::vector<std::weak_ptr<const C2Component>> &components =
+            mWrappedComponents.emplace_back();
+        components.push_back(wrapped);
+        components.push_back(comp);
+        for (const Component &filter : filters) {
+            components.push_back(filter.comp);
+        }
+    }
+    return wrapped;
+}
+
+bool FilterWrapper::isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) {
+    if (mInit != OK) {
+        LOG(WARNING) << "isFilteringEnabled: Wrapper not initialized: ";
+        return false;
+    }
+    return mPlugin->isFilteringEnabled(intf);
+}
+
+c2_status_t FilterWrapper::createBlockPool(
+        C2PlatformAllocatorStore::id_t allocatorId,
+        std::shared_ptr<const C2Component> component,
+        std::shared_ptr<C2BlockPool> *pool) {
+    std::unique_lock lock(mWrappedComponentsMutex);
+    for (auto it = mWrappedComponents.begin(); it != mWrappedComponents.end(); ) {
+        std::shared_ptr<const C2Component> comp = it->front().lock();
+        if (!comp) {
+            it = mWrappedComponents.erase(it);
+            continue;
+        }
+        if (component == comp) {
+            std::vector<std::shared_ptr<const C2Component>> components(it->size());
+            std::transform(
+                    it->begin(), it->end(), components.begin(),
+                    [](const std::weak_ptr<const C2Component> &el) {
+                        return el.lock();
+                    });
+            if (C2_OK == CreateCodec2BlockPool(allocatorId, components, pool)) {
+                return C2_OK;
+            }
+        }
+        ++it;
+    }
+    return CreateCodec2BlockPool(allocatorId, component, pool);
+}
+
+}  // namespace android
diff --git a/media/codec2/hidl/plugin/FilterWrapperStub.cpp b/media/codec2/hidl/plugin/FilterWrapperStub.cpp
new file mode 100644
index 0000000..1b94a1a
--- /dev/null
+++ b/media/codec2/hidl/plugin/FilterWrapperStub.cpp
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2020 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.
+ */
+
+//#define LOG_NDEBUG 0
+#define LOG_TAG "Codec2-FilterWrapperStub"
+
+#include <FilterWrapper.h>
+
+namespace android {
+
+FilterWrapper::FilterWrapper(std::unique_ptr<Plugin> &&) {
+}
+
+FilterWrapper::~FilterWrapper() {
+}
+
+std::shared_ptr<C2ComponentInterface> FilterWrapper::maybeWrapInterface(
+        const std::shared_ptr<C2ComponentInterface> intf) {
+    return intf;
+}
+
+std::shared_ptr<C2Component> FilterWrapper::maybeWrapComponent(
+        const std::shared_ptr<C2Component> comp) {
+    return comp;
+}
+
+bool FilterWrapper::isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &) {
+    return false;
+}
+
+c2_status_t FilterWrapper::createBlockPool(
+        C2PlatformAllocatorStore::id_t,
+        std::shared_ptr<const C2Component>,
+        std::shared_ptr<C2BlockPool> *) {
+    return C2_OMITTED;
+}
+
+}  // namespace android
diff --git a/media/codec2/hidl/plugin/include/codec2/hidl/plugin/FilterPlugin.h b/media/codec2/hidl/plugin/include/codec2/hidl/plugin/FilterPlugin.h
new file mode 100644
index 0000000..6f1f907
--- /dev/null
+++ b/media/codec2/hidl/plugin/include/codec2/hidl/plugin/FilterPlugin.h
@@ -0,0 +1,77 @@
+/*
+ * Copyright 2018, 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.
+ */
+
+#ifndef CODEC2_HIDL_PLUGIN_FILTER_PLUGIN_H
+
+#define CODEC2_HIDL_PLUGIN_FILTER_PLUGIN_H
+
+#include <memory>
+
+#include <C2Component.h>
+
+namespace android {
+
+class FilterPlugin_V1 {
+public:
+    static constexpr int32_t VERSION = 1;
+
+    virtual ~FilterPlugin_V1() = default;
+
+    /**
+     * Returns a C2ComponentStore object with which clients can create
+     * filter components / interfaces.
+     */
+    virtual std::shared_ptr<C2ComponentStore> getComponentStore() = 0;
+    struct Descriptor {
+        // Parameters that client sets for filter control.
+        std::initializer_list<C2Param::Type> controlParams;
+        // Parameters that the component changes after filtering.
+        std::initializer_list<C2Param::Type> affectedParams;
+    };
+
+    /**
+     * Describe a filter component.
+     *
+     * @param name[in]  filter's name
+     * @param desc[out] pointer to filter descriptor to be populated
+     * @return  true if |name| is in the store and |desc| is populated;
+     *          false if |name| is not recognized
+     */
+    virtual bool describe(C2String name, Descriptor *desc) = 0;
+
+    /**
+     * Returns true if a component will apply filtering after all given the
+     * current configuration; false if it will be no-op.
+     */
+    virtual bool isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) = 0;
+};
+
+}  // namespace android
+
+extern "C" {
+
+typedef int32_t (*GetFilterPluginVersionFunc)();
+int32_t GetFilterPluginVersion();
+
+typedef void* (*CreateFilterPluginFunc)();
+void *CreateFilterPlugin();
+
+typedef void (*DestroyFilterPluginFunc)(void *);
+void DestroyFilterPlugin(void *plugin);
+
+}  // extern "C"
+
+#endif  // CODEC2_HIDL_PLUGIN_FILTER_PLUGIN_H
diff --git a/media/codec2/hidl/plugin/internal/DefaultFilterPlugin.h b/media/codec2/hidl/plugin/internal/DefaultFilterPlugin.h
new file mode 100644
index 0000000..f856324
--- /dev/null
+++ b/media/codec2/hidl/plugin/internal/DefaultFilterPlugin.h
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2020, 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.
+ */
+
+#ifndef CODEC2_HIDL_PLUGIN_DEFAULT_FILTER_PLUGIN_H
+
+#define CODEC2_HIDL_PLUGIN_DEFAULT_FILTER_PLUGIN_H
+
+#include <codec2/hidl/plugin/FilterPlugin.h>
+
+#include <FilterWrapper.h>
+
+namespace android {
+
+class DefaultFilterPlugin : public FilterWrapper::Plugin {
+public:
+    explicit DefaultFilterPlugin(const char *pluginPath);
+
+    ~DefaultFilterPlugin();
+
+    status_t status() const override { return mInit; }
+
+    std::shared_ptr<C2ComponentStore> getStore() override { return mStore; }
+    bool describe(C2String name, FilterWrapper::Descriptor *desc) override;
+    bool isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) override;
+
+private:
+    status_t mInit;
+    void *mHandle;
+    DestroyFilterPluginFunc mDestroyPlugin;
+    FilterPlugin_V1 *mPlugin;
+    std::shared_ptr<C2ComponentStore> mStore;
+};
+
+}  // namespace android
+
+#endif  // CODEC2_HIDL_PLUGIN_DEFAULT_FILTER_PLUGIN_H
diff --git a/media/codec2/hidl/plugin/internal/FilterWrapper.h b/media/codec2/hidl/plugin/internal/FilterWrapper.h
new file mode 100644
index 0000000..5ced435
--- /dev/null
+++ b/media/codec2/hidl/plugin/internal/FilterWrapper.h
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2020, 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.
+ */
+
+#ifndef CODEC2_HIDL_PLUGIN_FILTER_WRAPPER_H
+
+#define CODEC2_HIDL_PLUGIN_FILTER_WRAPPER_H
+
+#include <map>
+#include <memory>
+#include <mutex>
+
+#include <C2Component.h>
+#include <C2PlatformSupport.h>
+
+#include <codec2/hidl/plugin/FilterPlugin.h>
+#include <utils/Errors.h>
+
+namespace android {
+
+// TODO: documentation
+class FilterWrapper : public std::enable_shared_from_this<FilterWrapper> {
+public:
+    using Descriptor = FilterPlugin_V1::Descriptor;
+
+    class Plugin {
+    public:
+        Plugin() = default;
+        virtual ~Plugin() = default;
+        virtual status_t status() const = 0;
+        virtual std::shared_ptr<C2ComponentStore> getStore() = 0;
+        virtual bool describe(C2String name, Descriptor *desc) = 0;
+        virtual bool isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) = 0;
+        C2_DO_NOT_COPY(Plugin);
+    };
+
+    struct Component {
+        const std::shared_ptr<C2Component> comp;
+        const std::shared_ptr<C2ComponentInterface> intf;
+        const C2Component::Traits traits;
+        const Descriptor desc;
+    };
+
+private:
+    explicit FilterWrapper(std::unique_ptr<Plugin> &&plugin);
+public:
+    static std::shared_ptr<FilterWrapper> Create(std::unique_ptr<Plugin> &&plugin) {
+        return std::shared_ptr<FilterWrapper>(new FilterWrapper(std::move(plugin)));
+    }
+    ~FilterWrapper();
+
+    /**
+     * Returns wrapped interface, or |intf| if wrapping is not possible / needed.
+     */
+    std::shared_ptr<C2ComponentInterface> maybeWrapInterface(
+            const std::shared_ptr<C2ComponentInterface> intf);
+
+    /**
+     * Returns wrapped component, or |comp| if wrapping is not possible / needed.
+     */
+    std::shared_ptr<C2Component> maybeWrapComponent(
+            const std::shared_ptr<C2Component> comp);
+
+    /**
+     * Returns ture iff the filtering will apply to the buffer in current configuration.
+     */
+    bool isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf);
+
+    c2_status_t createBlockPool(
+            C2PlatformAllocatorStore::id_t allocatorId,
+            std::shared_ptr<const C2Component> component,
+            std::shared_ptr<C2BlockPool> *pool);
+
+private:
+    status_t mInit;
+    std::unique_ptr<Plugin> mPlugin;
+    std::shared_ptr<C2ComponentStore> mStore;
+    std::list<FilterWrapper::Component> mComponents;
+
+    std::mutex mCacheMutex;
+    std::map<std::string, C2Component::Traits> mCachedTraits;
+
+    std::mutex mWrappedComponentsMutex;
+    std::list<std::vector<std::weak_ptr<const C2Component>>> mWrappedComponents;
+
+    std::vector<FilterWrapper::Component> createFilters();
+    C2Component::Traits getTraits(const std::shared_ptr<C2ComponentInterface> &intf);
+
+    C2_DO_NOT_COPY(FilterWrapper);
+};
+
+}  // namespace android
+
+#endif  // CODEC2_HIDL_PLUGIN_FILTER_WRAPPER_H
diff --git a/media/codec2/hidl/plugin/samples/Android.bp b/media/codec2/hidl/plugin/samples/Android.bp
new file mode 100644
index 0000000..c823e31
--- /dev/null
+++ b/media/codec2/hidl/plugin/samples/Android.bp
@@ -0,0 +1,49 @@
+cc_defaults {
+    name: "sample-codec2-hidl-plugin-defaults",
+
+    srcs: [
+        "SampleFilterPlugin.cpp",
+    ],
+
+    defaults: [
+        "libcodec2-impl-defaults",
+    ],
+
+    header_libs: [
+        "libcodec2_hidl_plugin_headers",
+        "libgui_headers",
+    ],
+
+    shared_libs: [
+        "libEGL",
+        "libGLESv1_CM",
+        "libGLESv2",
+        "libGLESv3",
+        "libbase",
+        "libcodec2",
+        "libcutils",
+        "libprocessgroup",
+        "libsfplugin_ccodec_utils",
+        "libsync",
+        "libui",
+        "libutils",
+    ],
+
+    static_libs: [
+        "librenderfright",
+    ],
+
+    cflags: [
+        "-Werror",
+        "-Wall",
+    ],
+}
+
+cc_library {
+    name: "sample-codec2-hidl-plugin",
+    vendor: true,
+
+    defaults: [
+        "sample-codec2-hidl-plugin-defaults",
+    ],
+}
diff --git a/media/codec2/hidl/plugin/samples/SampleFilterPlugin.cpp b/media/codec2/hidl/plugin/samples/SampleFilterPlugin.cpp
new file mode 100644
index 0000000..94811fc
--- /dev/null
+++ b/media/codec2/hidl/plugin/samples/SampleFilterPlugin.cpp
@@ -0,0 +1,969 @@
+/*
+ * Copyright 2020 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.
+ */
+
+#define LOG_TAG "SampleFilterPlugin"
+#include <android-base/logging.h>
+
+#include <chrono>
+#include <thread>
+
+#include <codec2/hidl/plugin/FilterPlugin.h>
+
+#include <C2AllocatorGralloc.h>
+#include <C2Config.h>
+#include <C2PlatformSupport.h>
+#include <Codec2Mapper.h>
+#include <util/C2InterfaceHelper.h>
+
+#include <renderengine/RenderEngine.h>
+#include <system/window.h>
+#include <ui/GraphicBuffer.h>
+#include <utils/RefBase.h>
+
+typedef C2StreamParam<C2Info, C2ColorAspectsStruct,
+                kParamIndexColorAspects | C2Param::CoreIndex::IS_REQUEST_FLAG>
+        C2StreamColorAspectsRequestInfo;
+
+namespace android {
+
+using namespace std::literals::chrono_literals;
+
+class SampleToneMappingFilter
+    : public C2Component, public std::enable_shared_from_this<SampleToneMappingFilter> {
+public:
+    class Interface : public C2ComponentInterface {
+    public:
+        static const std::string NAME;
+        static const FilterPlugin_V1::Descriptor DESCRIPTOR;
+
+        explicit Interface(c2_node_id_t id)
+            : mId(id),
+              mReflector(std::make_shared<C2ReflectorHelper>()),
+              mHelper(mReflector) {
+        }
+        ~Interface() override = default;
+        C2String getName() const override { return NAME; }
+        c2_node_id_t getId() const override { return mId; }
+
+        c2_status_t query_vb(
+                const std::vector<C2Param*> &stackParams,
+                const std::vector<C2Param::Index> &heapParamIndices,
+                c2_blocking_t mayBlock,
+                std::vector<std::unique_ptr<C2Param>>* const heapParams) const override {
+            return mHelper.query(stackParams, heapParamIndices, mayBlock, heapParams);
+        }
+        c2_status_t config_vb(
+                const std::vector<C2Param*> &params,
+                c2_blocking_t mayBlock,
+                std::vector<std::unique_ptr<C2SettingResult>>* const failures) override {
+            return mHelper.config(params, mayBlock, failures);
+        }
+        c2_status_t querySupportedParams_nb(
+                std::vector<std::shared_ptr<C2ParamDescriptor>> * const params) const override {
+            return mHelper.querySupportedParams(params);
+        }
+        c2_status_t querySupportedValues_vb(
+                std::vector<C2FieldSupportedValuesQuery> &fields,
+                c2_blocking_t mayBlock) const override {
+            return mHelper.querySupportedValues(fields, mayBlock);
+        }
+        c2_status_t createTunnel_sm(c2_node_id_t) override { return C2_OMITTED; }
+        c2_status_t releaseTunnel_sm(c2_node_id_t) override { return C2_OMITTED; }
+
+        uint32_t getDataSpace() {
+            Helper::Lock lock = mHelper.lock();
+            uint32_t dataspace = HAL_DATASPACE_UNKNOWN;
+            C2Mapper::map(
+                    mHelper.mInputColorAspectInfo->range,
+                    mHelper.mInputColorAspectInfo->primaries,
+                    mHelper.mInputColorAspectInfo->matrix,
+                    mHelper.mInputColorAspectInfo->transfer,
+                    &dataspace);
+            return dataspace;
+        }
+        std::shared_ptr<C2StreamHdrStaticInfo::input> getHdrStaticMetadata() {
+            Helper::Lock lock = mHelper.lock();
+            return mHelper.mInputHdrStaticInfo;
+        }
+        C2BlockPool::local_id_t getPoolId() {
+            Helper::Lock lock = mHelper.lock();
+            return mHelper.mOutputPoolIds->m.values[0];
+        }
+
+        static bool IsFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) {
+            C2StreamColorAspectsRequestInfo::output info(0u);
+            std::vector<std::unique_ptr<C2Param>> heapParams;
+            c2_status_t err = intf->query_vb({&info}, {}, C2_MAY_BLOCK, &heapParams);
+            if (err != C2_OK && err != C2_BAD_INDEX) {
+                LOG(WARNING) << "SampleToneMappingFilter::Interface::IsFilteringEnabled: "
+                        << "query failed for " << intf->getName();
+                return false;
+            }
+            return info && info.transfer == C2Color::TRANSFER_170M;
+        }
+    private:
+        const c2_node_id_t mId;
+        std::shared_ptr<C2ReflectorHelper> mReflector;
+        struct Helper : public C2InterfaceHelper {
+            explicit Helper(std::shared_ptr<C2ReflectorHelper> reflector)
+                : C2InterfaceHelper(reflector) {
+                setDerivedInstance(this);
+
+                addParameter(
+                        DefineParam(mApiFeatures, C2_PARAMKEY_API_FEATURES)
+                        .withConstValue(new C2ApiFeaturesSetting(C2Config::api_feature_t(
+                                API_REFLECTION |
+                                API_VALUES |
+                                API_CURRENT_VALUES |
+                                API_DEPENDENCY |
+                                API_SAME_INPUT_BUFFER)))
+                        .build());
+
+                mName = C2ComponentNameSetting::AllocShared(NAME.size() + 1);
+                strncpy(mName->m.value, NAME.c_str(), NAME.size() + 1);
+                addParameter(
+                        DefineParam(mName, C2_PARAMKEY_COMPONENT_NAME)
+                        .withConstValue(mName)
+                        .build());
+
+                addParameter(
+                        DefineParam(mKind, C2_PARAMKEY_COMPONENT_KIND)
+                        .withConstValue(new C2ComponentKindSetting(C2Component::KIND_OTHER))
+                        .build());
+
+                addParameter(
+                        DefineParam(mDomain, C2_PARAMKEY_COMPONENT_DOMAIN)
+                        .withConstValue(new C2ComponentDomainSetting(C2Component::DOMAIN_VIDEO))
+                        .build());
+
+                addParameter(
+                        DefineParam(mInputStreamCount, C2_PARAMKEY_INPUT_STREAM_COUNT)
+                        .withConstValue(new C2PortStreamCountTuning::input(1))
+                        .build());
+
+                addParameter(
+                        DefineParam(mOutputStreamCount, C2_PARAMKEY_OUTPUT_STREAM_COUNT)
+                        .withConstValue(new C2PortStreamCountTuning::output(1))
+                        .build());
+
+                addParameter(
+                        DefineParam(mInputFormat, C2_PARAMKEY_INPUT_STREAM_BUFFER_TYPE)
+                        .withConstValue(new C2StreamBufferTypeSetting::input(
+                                0u, C2BufferData::GRAPHIC))
+                        .build());
+
+                static const std::string kRawMediaType = "video/raw";
+                mInputMediaType = C2PortMediaTypeSetting::input::AllocShared(
+                        kRawMediaType.size() + 1);
+                strncpy(mInputMediaType->m.value, kRawMediaType.c_str(), kRawMediaType.size() + 1);
+                addParameter(
+                        DefineParam(mInputMediaType, C2_PARAMKEY_INPUT_MEDIA_TYPE)
+                        .withConstValue(mInputMediaType)
+                        .build());
+
+                addParameter(
+                        DefineParam(mOutputFormat, C2_PARAMKEY_OUTPUT_STREAM_BUFFER_TYPE)
+                        .withConstValue(new C2StreamBufferTypeSetting::output(
+                                0u, C2BufferData::GRAPHIC))
+                        .build());
+
+                mOutputMediaType = C2PortMediaTypeSetting::output::AllocShared(
+                        kRawMediaType.size() + 1);
+                strncpy(mOutputMediaType->m.value, kRawMediaType.c_str(), kRawMediaType.size() + 1);
+                addParameter(
+                        DefineParam(mOutputMediaType, C2_PARAMKEY_OUTPUT_MEDIA_TYPE)
+                        .withConstValue(mOutputMediaType)
+                        .build());
+
+                addParameter(
+                        DefineParam(mActualInputDelay, C2_PARAMKEY_INPUT_DELAY)
+                        .withConstValue(new C2PortActualDelayTuning::input(0u))
+                        .build());
+
+                addParameter(
+                        DefineParam(mActualOutputDelay, C2_PARAMKEY_OUTPUT_DELAY)
+                        .withConstValue(new C2PortActualDelayTuning::output(0u))
+                        .build());
+
+                addParameter(
+                        DefineParam(mActualPipelineDelay, C2_PARAMKEY_PIPELINE_DELAY)
+                        .withConstValue(new C2ActualPipelineDelayTuning(0u))
+                        .build());
+
+                C2BlockPool::local_id_t outputPoolIds[1] = { C2BlockPool::BASIC_GRAPHIC };
+                addParameter(
+                        DefineParam(mOutputPoolIds, C2_PARAMKEY_OUTPUT_BLOCK_POOLS)
+                        .withDefault(C2PortBlockPoolsTuning::output::AllocShared(outputPoolIds))
+                        .withFields({ C2F(mOutputPoolIds, m.values[0]).any(),
+                                      C2F(mOutputPoolIds, m.values).inRange(0, 1) })
+                        .withSetter(OutputBlockPoolSetter)
+                        .build());
+
+                addParameter(
+                        DefineParam(mInputHdrStaticInfo, C2_PARAMKEY_HDR_STATIC_INFO)
+                        .withDefault(new C2StreamHdrStaticInfo::input(0u))
+                        .withFields({
+                            C2F(mInputHdrStaticInfo, mastering.red.x).any(),
+                        })
+                        .withSetter(HdrStaticInfoSetter)
+                        .build());
+
+                addParameter(
+                        DefineParam(mOutputHdrStaticInfo, C2_PARAMKEY_HDR_STATIC_INFO)
+                        .withConstValue(new C2StreamHdrStaticInfo::output(0u))
+                        .build());
+
+                addParameter(
+                        DefineParam(mInputColorAspectInfo, C2_PARAMKEY_COLOR_ASPECTS)
+                        .withDefault(new C2StreamColorAspectsInfo::input(0u))
+                        .withFields({
+                            C2F(mInputColorAspectInfo, range).any(),
+                            C2F(mInputColorAspectInfo, primaries).any(),
+                            C2F(mInputColorAspectInfo, transfer).any(),
+                            C2F(mInputColorAspectInfo, matrix).any(),
+                        })
+                        .withSetter(InputColorAspectsSetter)
+                        .build());
+
+                addParameter(
+                        DefineParam(
+                            mColorAspectRequestInfo,
+                            (std::string(C2_PARAMKEY_COLOR_ASPECTS) + ".request").c_str())
+                        .withDefault(new C2StreamColorAspectsRequestInfo::output(0u))
+                        .withFields({
+                            C2F(mColorAspectRequestInfo, range).any(),
+                            C2F(mColorAspectRequestInfo, primaries).any(),
+                            C2F(mColorAspectRequestInfo, transfer).oneOf({
+                                C2Color::TRANSFER_UNSPECIFIED,
+                                C2Color::TRANSFER_170M,
+                            }),
+                            C2F(mColorAspectRequestInfo, matrix).any(),
+                        })
+                        .withSetter(ColorAspectsRequestSetter)
+                        .build());
+
+                addParameter(
+                        DefineParam(mOutputColorAspectInfo, C2_PARAMKEY_COLOR_ASPECTS)
+                        .withDefault(new C2StreamColorAspectsInfo::output(0u))
+                        .withFields({
+                            C2F(mOutputColorAspectInfo, range).any(),
+                            C2F(mOutputColorAspectInfo, primaries).any(),
+                            C2F(mOutputColorAspectInfo, transfer).any(),
+                            C2F(mOutputColorAspectInfo, matrix).any(),
+                        })
+                        .withSetter(OutputColorAspectsSetter,
+                                    mInputColorAspectInfo,
+                                    mColorAspectRequestInfo)
+                        .build());
+            }
+
+            static C2R OutputBlockPoolSetter(
+                    bool mayBlock,
+                    C2P<C2PortBlockPoolsTuning::output> &me) {
+                (void)mayBlock, (void)me;
+                return C2R::Ok();
+            }
+
+            static C2R HdrStaticInfoSetter(
+                    bool mayBlock,
+                    C2P<C2StreamHdrStaticInfo::input> &me) {
+                (void)mayBlock, (void)me;
+                return C2R::Ok();
+            }
+
+            static C2R InputColorAspectsSetter(
+                    bool mayBlock,
+                    C2P<C2StreamColorAspectsInfo::input> &me) {
+                (void)mayBlock, (void)me;
+                return C2R::Ok();
+            }
+
+            static C2R OutputColorAspectsSetter(
+                    bool mayBlock,
+                    C2P<C2StreamColorAspectsInfo::output> &me,
+                    const C2P<C2StreamColorAspectsInfo::input> &inputColor,
+                    const C2P<C2StreamColorAspectsRequestInfo::output> &request) {
+                (void)mayBlock;
+                me.set().range = inputColor.v.range;
+                me.set().primaries = inputColor.v.primaries;
+                me.set().transfer = inputColor.v.transfer;
+                if (request.v.transfer == C2Color::TRANSFER_170M) {
+                    me.set().transfer = C2Color::TRANSFER_170M;
+                }
+                me.set().matrix = inputColor.v.matrix;
+                return C2R::Ok();
+            }
+
+            static C2R ColorAspectsRequestSetter(
+                    bool mayBlock,
+                    C2P<C2StreamColorAspectsRequestInfo::output> &me) {
+                (void)mayBlock;
+                if (me.v.range != C2Color::RANGE_UNSPECIFIED) {
+                    me.set().range = C2Color::RANGE_UNSPECIFIED;
+                }
+                if (me.v.primaries != C2Color::PRIMARIES_UNSPECIFIED) {
+                    me.set().primaries = C2Color::PRIMARIES_UNSPECIFIED;
+                }
+                if (me.v.transfer != C2Color::TRANSFER_170M) {
+                    me.set().transfer = C2Color::TRANSFER_UNSPECIFIED;
+                }
+                if (me.v.matrix != C2Color::MATRIX_UNSPECIFIED) {
+                    me.set().matrix = C2Color::MATRIX_UNSPECIFIED;
+                }
+                return C2R::Ok();
+            }
+
+            std::shared_ptr<C2ApiFeaturesSetting> mApiFeatures;
+
+            std::shared_ptr<C2ComponentNameSetting> mName;
+            std::shared_ptr<C2ComponentAliasesSetting> mAliases;
+            std::shared_ptr<C2ComponentKindSetting> mKind;
+            std::shared_ptr<C2ComponentDomainSetting> mDomain;
+
+            std::shared_ptr<C2PortMediaTypeSetting::input> mInputMediaType;
+            std::shared_ptr<C2PortMediaTypeSetting::output> mOutputMediaType;
+            std::shared_ptr<C2StreamBufferTypeSetting::input> mInputFormat;
+            std::shared_ptr<C2StreamBufferTypeSetting::output> mOutputFormat;
+
+            std::shared_ptr<C2PortActualDelayTuning::input> mActualInputDelay;
+            std::shared_ptr<C2PortActualDelayTuning::output> mActualOutputDelay;
+            std::shared_ptr<C2ActualPipelineDelayTuning> mActualPipelineDelay;
+
+            std::shared_ptr<C2PortStreamCountTuning::input> mInputStreamCount;
+            std::shared_ptr<C2PortStreamCountTuning::output> mOutputStreamCount;
+
+            std::shared_ptr<C2PortBlockPoolsTuning::output> mOutputPoolIds;
+
+            std::shared_ptr<C2StreamHdrStaticInfo::input> mInputHdrStaticInfo;
+            std::shared_ptr<C2StreamHdrStaticInfo::output> mOutputHdrStaticInfo;
+            std::shared_ptr<C2StreamColorAspectsInfo::input> mInputColorAspectInfo;
+            std::shared_ptr<C2StreamColorAspectsInfo::output> mOutputColorAspectInfo;
+            std::shared_ptr<C2StreamColorAspectsRequestInfo::output> mColorAspectRequestInfo;
+        } mHelper;
+    };
+
+    explicit SampleToneMappingFilter(c2_node_id_t id)
+        : mIntf(std::make_shared<Interface>(id)) {
+    }
+    ~SampleToneMappingFilter() override {
+        if (mProcessingThread.joinable()) {
+            mProcessingThread.join();
+        }
+    }
+
+    c2_status_t setListener_vb(
+            const std::shared_ptr<Listener> &listener, c2_blocking_t mayBlock) override {
+        std::chrono::steady_clock::time_point deadline = std::chrono::steady_clock::now() + 5ms;
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState == RELEASED) {
+                return C2_BAD_STATE;
+            }
+            if (mState == RUNNING && listener) {
+                return C2_BAD_STATE;
+            }
+            if (mState != STOPPED) {
+                return C2_BAD_STATE;
+            }
+        }
+        std::unique_lock lock(mListenerMutex, std::try_to_lock);
+        if (lock) {
+            mListener = listener;
+            return C2_OK;
+        }
+        if (mayBlock == C2_DONT_BLOCK) {
+            return C2_BLOCKING;
+        }
+        lock.try_lock_until(deadline);
+        if (!lock) {
+            return C2_TIMED_OUT;
+        }
+        mListener = listener;
+        return C2_OK;
+    }
+
+    c2_status_t queue_nb(std::list<std::unique_ptr<C2Work>>* const items) override {
+        if (!items) {
+            return C2_BAD_VALUE;
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState != RUNNING) {
+                return C2_BAD_STATE;
+            }
+        }
+        std::unique_lock lock(mQueueMutex);
+        mQueue.splice(mQueue.end(), *items);
+        return C2_OK;
+    }
+
+    c2_status_t announce_nb(const std::vector<C2WorkOutline> &) override { return C2_OMITTED; }
+
+    c2_status_t flush_sm(
+            flush_mode_t mode,
+            std::list<std::unique_ptr<C2Work>>* const flushedWork) override {
+        if (!flushedWork) {
+            return C2_BAD_VALUE;
+        }
+        if (mode == FLUSH_CHAIN) {
+            return C2_BAD_VALUE;
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState != RUNNING) {
+                return C2_BAD_STATE;
+            }
+        }
+        {
+            std::unique_lock lock(mQueueMutex);
+            mQueue.swap(*flushedWork);
+        }
+        // NOTE: this component does not have internal state to flush.
+        return C2_OK;
+    }
+
+    c2_status_t drain_nb(drain_mode_t mode) override {
+        if (mode == DRAIN_CHAIN) {
+            return C2_BAD_VALUE;
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState != RUNNING) {
+                return C2_BAD_STATE;
+            }
+        }
+        // NOTE: this component does not wait for work items before processing.
+        return C2_OK;
+    }
+
+    c2_status_t start() override {
+        //std::chrono::steady_clock::time_point deadline = std::chrono::steady_clock::now() + 500ms;
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState == STARTING) {
+                return C2_DUPLICATE;
+            }
+            if (mState != STOPPED) {
+                return C2_BAD_STATE;
+            }
+            mState = STARTING;
+        }
+        {
+            std::unique_lock lock(mProcessingMutex);
+            if (!mProcessingThread.joinable()) {
+                mProcessingThread = std::thread([this]() {
+                    processLoop(shared_from_this());
+                });
+            }
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            mState = RUNNING;
+        }
+        return C2_OK;
+    }
+
+    c2_status_t stop() override {
+        //std::chrono::steady_clock::time_point deadline = std::chrono::steady_clock::now() + 500ms;
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState == STOPPING) {
+                return C2_DUPLICATE;
+            }
+            if (mState != RUNNING) {
+                return C2_BAD_STATE;
+            }
+            mState = STOPPING;
+        }
+        {
+            std::unique_lock lock(mQueueMutex);
+            mQueueCondition.notify_all();
+        }
+        {
+            std::unique_lock lock(mProcessingMutex);
+            if (mProcessingThread.joinable()) {
+                mProcessingThread.join();
+            }
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            mState = STOPPED;
+        }
+        return C2_OK;
+    }
+
+    c2_status_t reset() override {
+        //std::chrono::steady_clock::time_point deadline = std::chrono::steady_clock::now() + 500ms;
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState == RESETTING) {
+                return C2_DUPLICATE;
+            }
+            if (mState == RELEASED) {
+                return C2_BAD_STATE;
+            }
+            mState = RESETTING;
+        }
+        {
+            std::unique_lock lock(mQueueMutex);
+            mQueueCondition.notify_all();
+        }
+        {
+            std::unique_lock lock(mProcessingMutex);
+            if (mProcessingThread.joinable()) {
+                mProcessingThread.join();
+            }
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            mState = STOPPED;
+        }
+        return C2_OK;
+    }
+
+    c2_status_t release() override {
+        //std::chrono::steady_clock::time_point deadline = std::chrono::steady_clock::now() + 500ms;
+        {
+            std::unique_lock lock(mStateMutex);
+            if (mState == RELEASED || mState == RELEASING) {
+                return C2_DUPLICATE;
+            }
+            // TODO: return C2_BAD_STATE if not stopped
+            mState = RELEASING;
+        }
+        {
+            std::unique_lock lock(mQueueMutex);
+            mQueueCondition.notify_all();
+        }
+        {
+            std::unique_lock lock(mProcessingMutex);
+            if (mProcessingThread.joinable()) {
+                mProcessingThread.join();
+            }
+        }
+        {
+            std::unique_lock lock(mStateMutex);
+            mState = RELEASED;
+        }
+        return C2_OK;
+    }
+
+    std::shared_ptr<C2ComponentInterface> intf() override {
+        return mIntf;
+    }
+
+private:
+    void processLoop(std::shared_ptr<SampleToneMappingFilter> thiz) {
+        constexpr float kDefaultMaxLumiance = 500.0;
+        constexpr float kDefaultMaxMasteringLuminance = 1000.0;
+        constexpr float kDefaultMaxContentLuminance = 1000.0;
+        constexpr uint32_t kDstUsage =
+                GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN |
+                GRALLOC_USAGE_HW_RENDER | GRALLOC_USAGE_HW_TEXTURE;
+
+        int32_t workCount = 0;
+        std::unique_ptr<renderengine::RenderEngine> renderEngine = renderengine::RenderEngine::create(
+                renderengine::RenderEngineCreationArgs::Builder()
+                    .setPixelFormat(static_cast<int>(ui::PixelFormat::RGBA_8888))
+                    .setImageCacheSize(2 /*maxFrameBufferAcquiredBuffers*/)
+                    .setUseColorManagerment(true)
+                    .setEnableProtectedContext(false)
+                    .setPrecacheToneMapperShaderOnly(true)
+                    .setContextPriority(renderengine::RenderEngine::ContextPriority::LOW)
+                    .build());
+        if (!renderEngine) {
+            std::unique_lock lock(mListenerMutex);
+            mListener->onError_nb(thiz, C2_CORRUPTED);
+            return;
+        }
+        uint32_t textureName = 0;
+        renderEngine->genTextures(1, &textureName);
+
+        while (true) {
+            // Before doing anything, verify the state
+            {
+                std::unique_lock lock(mStateMutex);
+                if (mState != RUNNING) {
+                    break;
+                }
+            }
+            // Extract one work item
+            std::unique_ptr<C2Work> work;
+            {
+                std::unique_lock lock(mQueueMutex);
+                if (mQueue.empty()) {
+                    mQueueCondition.wait_for(lock, 1s);
+                }
+                if (mQueue.empty()) {
+                    continue;
+                }
+                mQueue.front().swap(work);
+                mQueue.pop_front();
+                ++workCount;
+            }
+            LOG(VERBOSE) << "work #" << workCount << ": flags=" << work->input.flags
+                    << " timestamp=" << work->input.ordinal.timestamp.peek();;
+            std::shared_ptr<C2StreamHdrStaticInfo::input> hdrStaticInfo =
+                mIntf->getHdrStaticMetadata();
+            uint32_t dataspace = mIntf->getDataSpace();
+
+            std::shared_ptr<C2Buffer> buffer;
+            if (!work->input.buffers.empty()) {
+                buffer = work->input.buffers.front();
+            }
+            std::shared_ptr<C2Buffer> outC2Buffer;
+            status_t err = OK;
+            if (buffer) {
+                if (buffer->hasInfo(C2StreamHdrStaticInfo::output::PARAM_TYPE)) {
+                    std::shared_ptr<const C2Info> info =
+                        buffer->getInfo(C2StreamHdrStaticInfo::output::PARAM_TYPE);
+                    std::unique_ptr<C2Param> flipped = C2Param::CopyAsStream(
+                            *info, false /* output */, info->stream());
+                    hdrStaticInfo.reset(static_cast<C2StreamHdrStaticInfo::input *>(
+                            flipped.release()));
+                }
+                const C2Handle *c2Handle =
+                    buffer->data().graphicBlocks().front().handle();
+                uint32_t width, height, format, stride, igbp_slot, generation;
+                uint64_t usage, igbp_id;
+                _UnwrapNativeCodec2GrallocMetadata(
+                        c2Handle, &width, &height, &format, &usage, &stride, &generation,
+                        &igbp_id, &igbp_slot);
+                native_handle_t *grallocHandle = UnwrapNativeCodec2GrallocHandle(c2Handle);
+                sp<GraphicBuffer> srcBuffer = new GraphicBuffer(
+                        grallocHandle, GraphicBuffer::CLONE_HANDLE,
+                        width, height, format, 1, usage, stride);
+
+                std::shared_ptr<C2GraphicBlock> dstBlock;
+                C2BlockPool::local_id_t poolId = mIntf->getPoolId();
+                std::shared_ptr<C2BlockPool> pool;
+                GetCodec2BlockPool(poolId, thiz, &pool);
+                pool->fetchGraphicBlock(
+                        width, height, HAL_PIXEL_FORMAT_RGBA_8888, C2AndroidMemoryUsage::FromGrallocUsage(kDstUsage),
+                        &dstBlock);
+                outC2Buffer = C2Buffer::CreateGraphicBuffer(
+                        dstBlock->share(C2Rect(width, height), C2Fence()));
+                c2Handle = dstBlock->handle();
+                _UnwrapNativeCodec2GrallocMetadata(
+                        c2Handle, &width, &height, &format, &usage, &stride, &generation,
+                        &igbp_id, &igbp_slot);
+                grallocHandle = UnwrapNativeCodec2GrallocHandle(c2Handle);
+                sp<GraphicBuffer> dstBuffer = new GraphicBuffer(
+                        grallocHandle, GraphicBuffer::CLONE_HANDLE,
+                        width, height, format, 1, usage, stride);
+
+                Rect sourceCrop(0, 0, width, height);
+
+                renderengine::DisplaySettings clientCompositionDisplay;
+                std::vector<const renderengine::LayerSettings*> clientCompositionLayers;
+
+                clientCompositionDisplay.physicalDisplay = sourceCrop;
+                clientCompositionDisplay.clip = sourceCrop;
+
+                clientCompositionDisplay.outputDataspace = ui::Dataspace::V0_SRGB;
+                clientCompositionDisplay.maxLuminance = kDefaultMaxLumiance;
+                clientCompositionDisplay.clearRegion = Region::INVALID_REGION;
+                renderengine::LayerSettings layerSettings;
+                layerSettings.geometry.boundaries = sourceCrop.toFloatRect();
+                layerSettings.alpha = 1.0f;
+
+                layerSettings.sourceDataspace = static_cast<ui::Dataspace>(dataspace);
+
+                // from BufferLayer
+                layerSettings.source.buffer.buffer = srcBuffer;
+                layerSettings.source.buffer.isOpaque = true;
+                // TODO: fence
+                layerSettings.source.buffer.fence = Fence::NO_FENCE;
+                layerSettings.source.buffer.textureName = textureName;
+                layerSettings.source.buffer.usePremultipliedAlpha = false;
+                layerSettings.source.buffer.isY410BT2020 =
+                    (layerSettings.sourceDataspace == ui::Dataspace::BT2020_ITU_PQ ||
+                     layerSettings.sourceDataspace == ui::Dataspace::BT2020_ITU_HLG) &&
+                    format == HAL_PIXEL_FORMAT_RGBA_1010102;
+                layerSettings.source.buffer.maxMasteringLuminance =
+                    (hdrStaticInfo && *hdrStaticInfo &&
+                     hdrStaticInfo->mastering.maxLuminance > 0 &&
+                     hdrStaticInfo->mastering.minLuminance > 0)
+                        ? hdrStaticInfo->mastering.maxLuminance : kDefaultMaxMasteringLuminance;
+                layerSettings.source.buffer.maxContentLuminance =
+                    (hdrStaticInfo && *hdrStaticInfo && hdrStaticInfo->maxCll > 0)
+                        ? hdrStaticInfo->maxCll : kDefaultMaxContentLuminance;
+
+                // Set filtering to false since the capture itself doesn't involve
+                // any scaling, metadata retriever JNI is scaling the bitmap if
+                // display size is different from decoded size. If that scaling
+                // needs to be handled by server side, consider enable this based
+                // display size vs decoded size.
+                layerSettings.source.buffer.useTextureFiltering = false;
+                layerSettings.source.buffer.textureTransform = mat4();
+                clientCompositionLayers.push_back(&layerSettings);
+
+                // Use an empty fence for the buffer fence, since we just created the buffer so
+                // there is no need for synchronization with the GPU.
+                base::unique_fd bufferFence;
+                base::unique_fd drawFence;
+                renderEngine->useProtectedContext(false);
+                err = renderEngine->drawLayers(
+                        clientCompositionDisplay, clientCompositionLayers, dstBuffer.get(),
+                        /*useFramebufferCache=*/false, std::move(bufferFence), &drawFence);
+
+                sp<Fence> fence = new Fence(std::move(drawFence));
+
+                // We can move waiting for fence & sending it back on a separate thread to improve
+                // efficiency, but leaving it here for simplicity.
+                if (err != OK) {
+                    LOG(ERROR) << "drawLayers returned err " << err;
+                } else {
+                    err = fence->wait(500);
+                    if (err != OK) {
+                        LOG(WARNING) << "wait for fence returned err " << err;
+                    }
+                }
+                renderEngine->cleanupPostRender(renderengine::RenderEngine::CleanupMode::CLEAN_ALL);
+            }
+
+            work->worklets.front()->output.ordinal = work->input.ordinal;
+            work->worklets.front()->output.flags = work->input.flags;
+            if (err == OK) {
+                work->workletsProcessed = 1;
+                if (outC2Buffer) {
+                    work->worklets.front()->output.buffers.push_back(outC2Buffer);
+                }
+                work->result = C2_OK;
+            } else {
+                work->result = C2_CORRUPTED;
+            }
+            std::list<std::unique_ptr<C2Work>> items;
+            items.push_back(std::move(work));
+
+            std::unique_lock lock(mListenerMutex);
+            mListener->onWorkDone_nb(thiz, std::move(items));
+            LOG(VERBOSE) << "sent work #" << workCount;
+        }
+    }
+
+    mutable std::timed_mutex mListenerMutex;
+    std::shared_ptr<Listener> mListener;
+
+    mutable std::mutex mQueueMutex;
+    mutable std::condition_variable mQueueCondition;
+    std::list<std::unique_ptr<C2Work>> mQueue;
+
+    const std::shared_ptr<Interface> mIntf;
+
+    mutable std::mutex mStateMutex;
+    enum State {
+        STOPPED,
+        RUNNING,
+        RELEASED,
+        STARTING,   // STOPPED -> RUNNING
+        STOPPING,   // RUNNING -> STOPPED
+        RESETTING,  // <<ANY>> -> STOPPED
+        RELEASING,  // STOPPED -> RELEASED
+    } mState;
+
+    mutable std::mutex mProcessingMutex;
+    std::thread mProcessingThread;
+
+};
+
+// static
+const std::string SampleToneMappingFilter::Interface::NAME = "c2.sample.tone-mapper";
+// static
+const FilterPlugin_V1::Descriptor SampleToneMappingFilter::Interface::DESCRIPTOR = {
+    // controlParams
+    { C2StreamColorAspectsRequestInfo::output::PARAM_TYPE },
+    // affectedParams
+    {
+        C2StreamHdrStaticInfo::output::PARAM_TYPE,
+        C2StreamHdr10PlusInfo::output::PARAM_TYPE,
+        C2StreamColorAspectsInfo::output::PARAM_TYPE,
+    },
+};
+
+class SampleC2ComponentStore : public C2ComponentStore {
+public:
+    SampleC2ComponentStore()
+        : mReflector(std::make_shared<C2ReflectorHelper>()),
+          mIntf(mReflector),
+          mFactories(CreateFactories()) {
+    }
+    ~SampleC2ComponentStore() = default;
+
+    C2String getName() const override { return "android.sample.filter-plugin-store"; }
+    c2_status_t createComponent(
+            C2String name, std::shared_ptr<C2Component>* const component) override {
+        if (mFactories.count(name) == 0) {
+            return C2_BAD_VALUE;
+        }
+        return mFactories.at(name)->createComponent(++mNodeId, component);
+    }
+    c2_status_t createInterface(
+            C2String name, std::shared_ptr<C2ComponentInterface>* const interface) override {
+        if (mFactories.count(name) == 0) {
+            return C2_BAD_VALUE;
+        }
+        return mFactories.at(name)->createInterface(++mNodeId, interface);
+    }
+    std::vector<std::shared_ptr<const C2Component::Traits>> listComponents() override {
+        std::vector<std::shared_ptr<const C2Component::Traits>> ret;
+        for (const auto &[name, factory] : mFactories) {
+            ret.push_back(factory->getTraits());
+        }
+        return ret;
+    }
+    c2_status_t copyBuffer(
+            std::shared_ptr<C2GraphicBuffer>, std::shared_ptr<C2GraphicBuffer>) override {
+        return C2_OMITTED;
+    }
+    c2_status_t query_sm(
+            const std::vector<C2Param*> &stackParams,
+            const std::vector<C2Param::Index> &heapParamIndices,
+            std::vector<std::unique_ptr<C2Param>>* const heapParams) const override {
+        return mIntf.query(stackParams, heapParamIndices, C2_MAY_BLOCK, heapParams);
+    }
+    c2_status_t config_sm(
+            const std::vector<C2Param*> &params,
+            std::vector<std::unique_ptr<C2SettingResult>>* const failures) override {
+        return mIntf.config(params, C2_MAY_BLOCK, failures);
+    }
+    std::shared_ptr<C2ParamReflector> getParamReflector() const override {
+        return mReflector;
+    }
+    c2_status_t querySupportedParams_nb(
+            std::vector<std::shared_ptr<C2ParamDescriptor>> * const params) const override {
+        return mIntf.querySupportedParams(params);
+    }
+    c2_status_t querySupportedValues_sm(
+            std::vector<C2FieldSupportedValuesQuery> &fields) const override {
+        return mIntf.querySupportedValues(fields, C2_MAY_BLOCK);
+    }
+
+private:
+    class ComponentFactory {
+    public:
+        virtual ~ComponentFactory() = default;
+
+        const std::shared_ptr<const C2Component::Traits> &getTraits() { return mTraits; }
+
+        virtual c2_status_t createComponent(
+                c2_node_id_t id,
+                std::shared_ptr<C2Component>* const component) const = 0;
+        virtual c2_status_t createInterface(
+                c2_node_id_t id,
+                std::shared_ptr<C2ComponentInterface>* const interface) const = 0;
+    protected:
+        ComponentFactory(const std::shared_ptr<const C2Component::Traits> &traits)
+            : mTraits(traits) {
+        }
+    private:
+        const std::shared_ptr<const C2Component::Traits> mTraits;
+    };
+
+    template <class T>
+    struct ComponentFactoryImpl : public ComponentFactory {
+    public:
+        ComponentFactoryImpl(const std::shared_ptr<const C2Component::Traits> &traits)
+            : ComponentFactory(traits) {
+        }
+        ~ComponentFactoryImpl() override = default;
+        c2_status_t createComponent(
+                c2_node_id_t id,
+                std::shared_ptr<C2Component>* const component) const override {
+            *component = std::make_shared<T>(id);
+            return C2_OK;
+        }
+        c2_status_t createInterface(
+                c2_node_id_t id,
+                std::shared_ptr<C2ComponentInterface>* const interface) const override {
+            *interface = std::make_shared<typename T::Interface>(id);
+            return C2_OK;
+        }
+    };
+
+    template <class T>
+    static void AddFactory(std::map<C2String, std::unique_ptr<ComponentFactory>> *factories) {
+        std::shared_ptr<C2ComponentInterface> intf{new typename T::Interface(0)};
+        std::shared_ptr<C2Component::Traits> traits(new (std::nothrow) C2Component::Traits);
+        CHECK(C2InterfaceUtils::FillTraitsFromInterface(traits.get(), intf))
+                << "Failed to fill traits from interface";
+        factories->emplace(traits->name, new ComponentFactoryImpl<T>(traits));
+    }
+
+    static std::map<C2String, std::unique_ptr<ComponentFactory>> CreateFactories() {
+        std::map<C2String, std::unique_ptr<ComponentFactory>> factories;
+        AddFactory<SampleToneMappingFilter>(&factories);
+        return factories;
+    }
+
+
+    std::shared_ptr<C2ReflectorHelper> mReflector;
+    struct Interface : public C2InterfaceHelper {
+        explicit Interface(std::shared_ptr<C2ReflectorHelper> reflector)
+            : C2InterfaceHelper(reflector) {
+        }
+    } mIntf;
+
+    const std::map<C2String, std::unique_ptr<ComponentFactory>> mFactories;
+
+    std::atomic_int32_t mNodeId{0};
+};
+
+class SampleFilterPlugin : public FilterPlugin_V1 {
+public:
+    SampleFilterPlugin() : mStore(new SampleC2ComponentStore) {}
+    ~SampleFilterPlugin() override = default;
+
+    std::shared_ptr<C2ComponentStore> getComponentStore() override {
+        return mStore;
+    }
+
+    bool describe(C2String name, Descriptor *desc) override {
+        if (name == SampleToneMappingFilter::Interface::NAME) {
+            *desc = SampleToneMappingFilter::Interface::DESCRIPTOR;
+            return true;
+        }
+        return false;
+    }
+
+    bool isFilteringEnabled(const std::shared_ptr<C2ComponentInterface> &intf) override {
+        if (intf->getName() == SampleToneMappingFilter::Interface::NAME) {
+            return SampleToneMappingFilter::Interface::IsFilteringEnabled(intf);
+        }
+        return false;
+    }
+
+private:
+    std::shared_ptr<C2ComponentStore> mStore;
+};
+
+}  // namespace android
+
+extern "C" {
+
+int32_t GetFilterPluginVersion() {
+    return ::android::SampleFilterPlugin::VERSION;
+}
+
+void *CreateFilterPlugin() {
+    return new ::android::SampleFilterPlugin;
+}
+
+void DestroyFilterPlugin(void *plugin) {
+    delete (::android::SampleFilterPlugin *)plugin;
+}
+
+}  // extern "C"
diff --git a/media/codec2/sfplugin/CCodec.cpp b/media/codec2/sfplugin/CCodec.cpp
index 4fd0341..de0a129 100644
--- a/media/codec2/sfplugin/CCodec.cpp
+++ b/media/codec2/sfplugin/CCodec.cpp
@@ -1054,7 +1054,10 @@
         C2StreamMaxBufferSizeInfo::input maxInputSize(0u, 0u);
         C2PrependHeaderModeSetting prepend(PREPEND_HEADER_TO_NONE);
 
+        C2Param::Index colorAspectsRequestIndex =
+            C2StreamColorAspectsInfo::output::PARAM_TYPE | C2Param::CoreIndex::IS_REQUEST_FLAG;
         std::initializer_list<C2Param::Index> indices {
+            colorAspectsRequestIndex.withStream(0u),
         };
         c2_status_t c2err = comp->query(
                 { &usage, &maxInputSize, &prepend },
@@ -1065,11 +1068,6 @@
             ALOGE("Failed to query component interface: %d", c2err);
             return UNKNOWN_ERROR;
         }
-        if (params.size() != indices.size()) {
-            ALOGE("Component returns wrong number of params: expected %zu actual %zu",
-                    indices.size(), params.size());
-            return UNKNOWN_ERROR;
-        }
         if (usage) {
             if (usage.value & C2MemoryUsage::CPU_READ) {
                 config->mInputFormat->setInt32("using-sw-read-often", true);
@@ -1191,6 +1189,33 @@
             }
         }
 
+        std::unique_ptr<C2Param> colorTransferRequestParam;
+        for (std::unique_ptr<C2Param> &param : params) {
+            if (param->index() == colorAspectsRequestIndex.withStream(0u)) {
+                ALOGI("found color transfer request param");
+                colorTransferRequestParam = std::move(param);
+            }
+        }
+        int32_t colorTransferRequest = 0;
+        if (config->mDomain & (Config::IS_IMAGE | Config::IS_VIDEO)
+                && !sdkParams->findInt32("color-transfer-request", &colorTransferRequest)) {
+            colorTransferRequest = 0;
+        }
+
+        if (colorTransferRequest != 0) {
+            if (colorTransferRequestParam && *colorTransferRequestParam) {
+                C2StreamColorAspectsInfo::output *info =
+                    static_cast<C2StreamColorAspectsInfo::output *>(
+                            colorTransferRequestParam.get());
+                if (!C2Mapper::map(info->transfer, &colorTransferRequest)) {
+                    colorTransferRequest = 0;
+                }
+            } else {
+                colorTransferRequest = 0;
+            }
+            config->mInputFormat->setInt32("color-transfer-request", colorTransferRequest);
+        }
+
         ALOGD("setup formats input: %s and output: %s",
                 config->mInputFormat->debugString().c_str(),
                 config->mOutputFormat->debugString().c_str());
diff --git a/media/codec2/sfplugin/CCodecConfig.cpp b/media/codec2/sfplugin/CCodecConfig.cpp
index 5decb99..7214bf7 100644
--- a/media/codec2/sfplugin/CCodecConfig.cpp
+++ b/media/codec2/sfplugin/CCodecConfig.cpp
@@ -415,19 +415,37 @@
     add(ConfigMapper("color-matrix",        C2_PARAMKEY_DEFAULT_COLOR_ASPECTS,   "matrix")
         .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::CODED & (D::CONFIG | D::PARAM)));
 
+    // read back default for decoders. This is needed in case the component does not support
+    // color aspects. In that case, these values get copied to color-* keys.
+    add(ConfigMapper("default-color-range",     C2_PARAMKEY_DEFAULT_COLOR_ASPECTS,   "range")
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::CODED & D::READ)
+        .withC2Mappers<C2Color::range_t>());
+    add(ConfigMapper("default-color-transfer",  C2_PARAMKEY_DEFAULT_COLOR_ASPECTS,   "transfer")
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::CODED & D::READ)
+        .withC2Mappers<C2Color::transfer_t>());
+    add(ConfigMapper("default-color-primaries", C2_PARAMKEY_DEFAULT_COLOR_ASPECTS,   "primaries")
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::CODED & D::READ));
+    add(ConfigMapper("default-color-matrix",    C2_PARAMKEY_DEFAULT_COLOR_ASPECTS,   "matrix")
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::CODED & D::READ));
+
     // read back final for decoder output (also, configure final aspects as well. This should be
     // overwritten based on coded/default values if component supports color aspects, but is used
     // as final values if component does not support aspects at all)
     add(ConfigMapper(KEY_COLOR_RANGE,       C2_PARAMKEY_COLOR_ASPECTS,   "range")
-        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW)
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW & D::READ)
         .withC2Mappers<C2Color::range_t>());
     add(ConfigMapper(KEY_COLOR_TRANSFER,    C2_PARAMKEY_COLOR_ASPECTS,   "transfer")
-        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW)
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW & D::READ)
         .withC2Mappers<C2Color::transfer_t>());
     add(ConfigMapper("color-primaries",     C2_PARAMKEY_COLOR_ASPECTS,   "primaries")
-        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW));
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW & D::READ));
     add(ConfigMapper("color-matrix",        C2_PARAMKEY_COLOR_ASPECTS,   "matrix")
-        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW));
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW & D::READ));
+
+    // configure transfer request
+    add(ConfigMapper("color-transfer-request", C2_PARAMKEY_COLOR_ASPECTS, "transfer")
+        .limitTo((D::VIDEO | D::IMAGE) & D::DECODER  & D::RAW & D::CONFIG)
+        .withC2Mappers<C2Color::transfer_t>());
 
     // configure source aspects for encoders and read them back on the coded(!) port.
     // This is to ensure muxing the desired aspects into the container.
@@ -1001,11 +1019,14 @@
                     new C2StreamPixelAspectRatioInfo::output(0u, 1u, 1u),
                     C2_PARAMKEY_PIXEL_ASPECT_RATIO);
             addLocalParam(new C2StreamRotationInfo::output(0u, 0), C2_PARAMKEY_ROTATION);
-            addLocalParam(new C2StreamColorAspectsInfo::output(0u), C2_PARAMKEY_COLOR_ASPECTS);
+            addLocalParam(
+                    new C2StreamColorAspectsTuning::output(0u),
+                    C2_PARAMKEY_DEFAULT_COLOR_ASPECTS);
             addLocalParam<C2StreamDataSpaceInfo::output>(C2_PARAMKEY_DATA_SPACE);
             addLocalParam<C2StreamHdrStaticInfo::output>(C2_PARAMKEY_HDR_STATIC_INFO);
-            addLocalParam(new C2StreamSurfaceScalingInfo::output(0u, VIDEO_SCALING_MODE_SCALE_TO_FIT),
-                          C2_PARAMKEY_SURFACE_SCALING_MODE);
+            addLocalParam(
+                    new C2StreamSurfaceScalingInfo::output(0u, VIDEO_SCALING_MODE_SCALE_TO_FIT),
+                    C2_PARAMKEY_SURFACE_SCALING_MODE);
         } else {
             addLocalParam(new C2StreamColorAspectsInfo::input(0u), C2_PARAMKEY_COLOR_ASPECTS);
         }
@@ -1289,8 +1310,37 @@
     }
 
     { // convert color info
+        // move default color to color aspect if not read from the component
+        int32_t tmp;
+        int32_t range;
+        if (msg->findInt32("default-color-range", &range)) {
+            if (!msg->findInt32(KEY_COLOR_RANGE, &tmp)) {
+                msg->setInt32(KEY_COLOR_RANGE, range);
+            }
+            msg->removeEntryAt(msg->findEntryByName("default-color-range"));
+        }
+        int32_t transfer;
+        if (msg->findInt32("default-color-transfer", &transfer)) {
+            if (!msg->findInt32(KEY_COLOR_TRANSFER, &tmp)) {
+                msg->setInt32(KEY_COLOR_TRANSFER, transfer);
+            }
+            msg->removeEntryAt(msg->findEntryByName("default-color-transfer"));
+        }
         C2Color::primaries_t primaries;
+        if (msg->findInt32("default-color-primaries", (int32_t*)&primaries)) {
+            if (!msg->findInt32("color-primaries", &tmp)) {
+                msg->setInt32("color-primaries", primaries);
+            }
+            msg->removeEntryAt(msg->findEntryByName("default-color-primaries"));
+        }
         C2Color::matrix_t matrix;
+        if (msg->findInt32("default-color-matrix", (int32_t*)&matrix)) {
+            if (!msg->findInt32("color-matrix", &tmp)) {
+                msg->setInt32("color-matrix", matrix);
+            }
+            msg->removeEntryAt(msg->findEntryByName("default-color-matrix"));
+        }
+
         if (msg->findInt32("color-primaries", (int32_t*)&primaries)
                 && msg->findInt32("color-matrix", (int32_t*)&matrix)) {
             int32_t standard;
@@ -1382,22 +1432,22 @@
                 meta.sType1.mMinDisplayLuminance = hdr.mastering.minLuminance / 0.0001 + 0.5;
                 meta.sType1.mMaxContentLightLevel = hdr.maxCll + 0.5;
                 meta.sType1.mMaxFrameAverageLightLevel = hdr.maxFall + 0.5;
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.red.x"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.red.y"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.green.x"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.green.y"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.blue.x"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.blue.y"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.white.x"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.white.y"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.max-luminance"));
-                msg->removeEntryAt(msg->findEntryByName("smpte2086.min-luminance"));
-                msg->removeEntryAt(msg->findEntryByName("cta861.max-cll"));
-                msg->removeEntryAt(msg->findEntryByName("cta861.max-fall"));
                 msg->setBuffer(KEY_HDR_STATIC_INFO, ABuffer::CreateAsCopy(&meta, sizeof(meta)));
             } else {
                 ALOGD("found invalid HDR static metadata %s", msg->debugString(8).c_str());
             }
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.red.x"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.red.y"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.green.x"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.green.y"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.blue.x"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.blue.y"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.white.x"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.white.y"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.max-luminance"));
+            msg->removeEntryAt(msg->findEntryByName("smpte2086.min-luminance"));
+            msg->removeEntryAt(msg->findEntryByName("cta861.max-cll"));
+            msg->removeEntryAt(msg->findEntryByName("cta861.max-fall"));
         }
     }
 
@@ -1632,8 +1682,8 @@
             }
         }
     }
-    ALOGV("filtered %s to %s", params->debugString(4).c_str(),
-            filtered.debugString(4).c_str());
+    ALOGV("filter src msg %s", params->debugString(4).c_str());
+    ALOGV("filter dst params %s", filtered.debugString(4).c_str());
     return filtered;
 }
 
diff --git a/media/libaudioclient/AudioTrack.cpp b/media/libaudioclient/AudioTrack.cpp
index 57bd04f..a8255a5 100644
--- a/media/libaudioclient/AudioTrack.cpp
+++ b/media/libaudioclient/AudioTrack.cpp
@@ -1857,6 +1857,8 @@
         .set(AMEDIAMETRICS_PROP_FLAGS, toString(mFlags).c_str())
         .set(AMEDIAMETRICS_PROP_ORIGINALFLAGS, toString(mOrigFlags).c_str())
         .set(AMEDIAMETRICS_PROP_SESSIONID, (int32_t)mSessionId)
+        .set(AMEDIAMETRICS_PROP_LOGSESSIONID, mLogSessionId)
+        .set(AMEDIAMETRICS_PROP_PLAYERIID, mPlayerIId)
         .set(AMEDIAMETRICS_PROP_TRACKID, mPortId) // dup from key
         .set(AMEDIAMETRICS_PROP_CONTENTTYPE, toString(mAttributes.content_type).c_str())
         .set(AMEDIAMETRICS_PROP_USAGE, toString(mAttributes.usage).c_str())
@@ -3263,6 +3265,30 @@
     return mProxy->getUnderrunFrames();
 }
 
+void AudioTrack::setLogSessionId(const char *logSessionId)
+{
+     AutoMutex lock(mLock);
+    if (mLogSessionId == logSessionId) return;
+
+     mLogSessionId = logSessionId;
+     mediametrics::LogItem(mMetricsId)
+         .set(AMEDIAMETRICS_PROP_EVENT, AMEDIAMETRICS_PROP_EVENT_VALUE_SETLOGSESSIONID)
+         .set(AMEDIAMETRICS_PROP_LOGSESSIONID, logSessionId)
+         .record();
+}
+
+void AudioTrack::setPlayerIId(int playerIId)
+{
+    AutoMutex lock(mLock);
+    if (mPlayerIId == playerIId) return;
+
+    mPlayerIId = playerIId;
+    mediametrics::LogItem(mMetricsId)
+        .set(AMEDIAMETRICS_PROP_EVENT, AMEDIAMETRICS_PROP_EVENT_VALUE_SETPLAYERIID)
+        .set(AMEDIAMETRICS_PROP_PLAYERIID, playerIId)
+        .record();
+}
+
 status_t AudioTrack::addAudioDeviceCallback(const sp<AudioSystem::AudioDeviceCallback>& callback)
 {
 
diff --git a/media/libaudioclient/include/media/AudioTrack.h b/media/libaudioclient/include/media/AudioTrack.h
index e60ed55..51f1445 100644
--- a/media/libaudioclient/include/media/AudioTrack.h
+++ b/media/libaudioclient/include/media/AudioTrack.h
@@ -986,6 +986,22 @@
      */
             audio_port_handle_t getPortId() const { return mPortId; };
 
+    /* Sets the LogSessionId field which is used for metrics association of
+     * this object with other objects.
+     */
+            void setLogSessionId(const char *logSessionId);
+
+    /* Sets the playerIId field to associate the AudioTrack with an interface managed by
+     * AudioService.
+     *
+     * If this value is not set, then the playerIId is reported as -1
+     * (not associated with an AudioService player interface).
+     *
+     * For metrics purposes, we keep the playerIId association in the native
+     * client AudioTrack to improve the robustness under track restoration.
+     */
+            void setPlayerIId(int playerIId);
+
             void setAudioTrackCallback(const sp<media::IAudioTrackCallback>& callback) {
                 mAudioTrackCallback->setAudioTrackCallback(callback);
             }
@@ -1255,6 +1271,18 @@
     int                     mAuxEffectId;
     audio_port_handle_t     mPortId;                    // Id from Audio Policy Manager
 
+    /**
+     * mPlayerIId is the player id of the AudioTrack used by AudioManager.
+     * For an AudioTrack created by the Java interface, this is generally set once.
+     */
+    int                     mPlayerIId = -1;  // AudioManager.h PLAYER_PIID_INVALID
+
+    /**
+     * mLogSessionId is a string identifying this AudioTrack for the metrics service.
+     * It may be unique or shared with other objects.
+     */
+    std::string             mLogSessionId{};
+
     mutable Mutex           mLock;
 
     int                     mPreviousPriority;          // before start()
diff --git a/media/libmediametrics/include/MediaMetricsConstants.h b/media/libmediametrics/include/MediaMetricsConstants.h
index 2af7eee..a181b06 100644
--- a/media/libmediametrics/include/MediaMetricsConstants.h
+++ b/media/libmediametrics/include/MediaMetricsConstants.h
@@ -125,12 +125,14 @@
 #define AMEDIAMETRICS_PROP_INPUTDEVICES   "inputDevices"   // string value
 #define AMEDIAMETRICS_PROP_INTERVALCOUNT  "intervalCount"  // int32
 #define AMEDIAMETRICS_PROP_LATENCYMS      "latencyMs"      // double value
+#define AMEDIAMETRICS_PROP_LOGSESSIONID   "logSessionId"   // hex string, "" none
 #define AMEDIAMETRICS_PROP_NAME           "name"           // string value
 #define AMEDIAMETRICS_PROP_ORIGINALFLAGS  "originalFlags"  // int32
 #define AMEDIAMETRICS_PROP_OUTPUTDEVICES  "outputDevices"  // string value
 #define AMEDIAMETRICS_PROP_PERFORMANCEMODE "performanceMode"    // string value, "none", lowLatency"
 #define AMEDIAMETRICS_PROP_PLAYBACK_PITCH "playback.pitch" // double value (AudioTrack)
 #define AMEDIAMETRICS_PROP_PLAYBACK_SPEED "playback.speed" // double value (AudioTrack)
+#define AMEDIAMETRICS_PROP_PLAYERIID      "playerIId"      // int32 (-1 invalid/unset IID)
 #define AMEDIAMETRICS_PROP_ROUTEDDEVICEID "routedDeviceId" // int32
 #define AMEDIAMETRICS_PROP_SAMPLERATE     "sampleRate"     // int32
 #define AMEDIAMETRICS_PROP_SELECTEDDEVICEID "selectedDeviceId" // int32
@@ -181,7 +183,9 @@
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_RESTORE    "restore"
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_SETMODE    "setMode" // AudioFlinger
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_SETBUFFERSIZE    "setBufferSize" // AudioTrack
+#define AMEDIAMETRICS_PROP_EVENT_VALUE_SETLOGSESSIONID  "setLogSessionId" // AudioTrack, Record
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_SETPLAYBACKPARAM "setPlaybackParam" // AudioTrack
+#define AMEDIAMETRICS_PROP_EVENT_VALUE_SETPLAYERIID "setPlayerIId" // AudioTrack
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_SETVOICEVOLUME   "setVoiceVolume" // AudioFlinger
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_SETVOLUME  "setVolume"  // AudioTrack
 #define AMEDIAMETRICS_PROP_EVENT_VALUE_START      "start"  // AudioTrack, AudioRecord
diff --git a/media/libmediatranscoding/TranscodingClientManager.cpp b/media/libmediatranscoding/TranscodingClientManager.cpp
index b6a2381..76bb33e 100644
--- a/media/libmediatranscoding/TranscodingClientManager.cpp
+++ b/media/libmediatranscoding/TranscodingClientManager.cpp
@@ -315,6 +315,15 @@
 status_t TranscodingClientManager::addClient(
         const std::shared_ptr<ITranscodingClientCallback>& callback, const std::string& clientName,
         const std::string& opPackageName, std::shared_ptr<ITranscodingClient>* outClient) {
+    int32_t callingPid = AIBinder_getCallingPid();
+    int32_t callingUid = AIBinder_getCallingUid();
+
+    // Check if client has the permission
+    if (!isTrustedCaller(callingPid, callingUid)) {
+        ALOGE("addClient rejected (clientPid %d, clientUid %d)", callingPid, callingUid);
+        return IMediaTranscodingService::ERROR_PERMISSION_DENIED;
+    }
+
     // Validate the client.
     if (callback == nullptr || clientName.empty() || opPackageName.empty()) {
         ALOGE("Invalid client");
diff --git a/media/libstagefright/FrameDecoder.cpp b/media/libstagefright/FrameDecoder.cpp
index d11408d..a78e6d2 100644
--- a/media/libstagefright/FrameDecoder.cpp
+++ b/media/libstagefright/FrameDecoder.cpp
@@ -67,6 +67,12 @@
     if (trackMeta->findInt32(kKeySARWidth, &sarWidth)
             && trackMeta->findInt32(kKeySARHeight, &sarHeight)
             && sarHeight != 0) {
+        int32_t multVal;
+        if (width < 0 || sarWidth < 0 ||
+            __builtin_mul_overflow(width, sarWidth, &multVal)) {
+            ALOGE("displayWidth overflow %dx%d", width, sarWidth);
+            return NULL;
+        }
         displayWidth = (width * sarWidth) / sarHeight;
         displayHeight = height;
     } else if (trackMeta->findInt32(kKeyDisplayWidth, &displayWidth)
@@ -87,6 +93,16 @@
         rotationAngle = 0;
     }
 
+    if (!metaOnly) {
+        int32_t multVal;
+        if (width < 0 || height < 0 || dstBpp < 0 ||
+            __builtin_mul_overflow(dstBpp, width, &multVal) ||
+            __builtin_mul_overflow(multVal, height, &multVal)) {
+            ALOGE("Frame size overflow %dx%d bpp %d", width, height, dstBpp);
+            return NULL;
+        }
+    }
+
     VideoFrame frame(width, height, displayWidth, displayHeight,
             tileWidth, tileHeight, rotationAngle, dstBpp, !metaOnly, iccSize);
 
diff --git a/media/libstagefright/bqhelper/tests/Android.bp b/media/libstagefright/bqhelper/tests/Android.bp
index 6b53e38..95953ee 100644
--- a/media/libstagefright/bqhelper/tests/Android.bp
+++ b/media/libstagefright/bqhelper/tests/Android.bp
@@ -9,17 +9,19 @@
 
 cc_test {
     name: "FrameDropper_test",
-    test_suites: ["device-tests"],
-
+    test_suites: [
+        "device-tests",
+        "mts",
+    ],
     srcs: ["FrameDropper_test.cpp"],
-
     shared_libs: [
         "libstagefright_bufferqueue_helper",
         "libutils",
     ],
-
     cflags: [
         "-Werror",
         "-Wall",
     ],
+    compile_multilib: "first",
+
 }
diff --git a/media/libstagefright/include/media/stagefright/MediaCodecConstants.h b/media/libstagefright/include/media/stagefright/MediaCodecConstants.h
index d3ced29..619cb44 100644
--- a/media/libstagefright/include/media/stagefright/MediaCodecConstants.h
+++ b/media/libstagefright/include/media/stagefright/MediaCodecConstants.h
@@ -753,7 +753,7 @@
 constexpr char KEY_CA_SYSTEM_ID[] = "ca-system-id";
 constexpr char KEY_CA_PRIVATE_DATA[] = "ca-private-data";
 constexpr char KEY_CAPTURE_RATE[] = "capture-rate";
-constexpr char KEY_CHANNEL_COUNT[] = "channel-count";
+constexpr char KEY_CHANNEL_COUNT[] = "channel-count";   // value N, eq to range 1..N
 constexpr char KEY_CHANNEL_MASK[] = "channel-mask";
 constexpr char KEY_COLOR_FORMAT[] = "color-format";
 constexpr char KEY_COLOR_RANGE[] = "color-range";
@@ -808,6 +808,14 @@
 constexpr char KEY_TILE_HEIGHT[] = "tile-height";
 constexpr char KEY_TILE_WIDTH[] = "tile-width";
 constexpr char KEY_TRACK_ID[] = "track-id";
+constexpr char KEY_VIDEO_QP_B_MAX[] = "video-qp-b-max";
+constexpr char KEY_VIDEO_QP_B_MIN[] = "video-qp-b-min";
+constexpr char KEY_VIDEO_QP_I_MAX[] = "video-qp-i-max";
+constexpr char KEY_VIDEO_QP_I_MIN[] = "video-qp-i-min";
+constexpr char KEY_VIDEO_QP_MAX[] = "video-qp-max";
+constexpr char KEY_VIDEO_QP_MIN[] = "video-qp-min";
+constexpr char KEY_VIDEO_QP_P_MAX[] = "video-qp-p-max";
+constexpr char KEY_VIDEO_QP_P_MIN[] = "video-qp-p-min";
 constexpr char KEY_WIDTH[] = "width";
 
 // from MediaCodec.java
diff --git a/media/ndk/Android.bp b/media/ndk/Android.bp
index 8172334..3007574 100644
--- a/media/ndk/Android.bp
+++ b/media/ndk/Android.bp
@@ -276,5 +276,9 @@
         },
     },
 
-    apex_available: ["com.android.media"],
+    apex_available: [
+        "//apex_available:platform",
+        "com.android.media",
+        "com.android.media.swcodec",
+    ],
 }
diff --git a/media/ndk/NdkMediaFormat.cpp b/media/ndk/NdkMediaFormat.cpp
index 8e673ca..1773023 100644
--- a/media/ndk/NdkMediaFormat.cpp
+++ b/media/ndk/NdkMediaFormat.cpp
@@ -383,6 +383,14 @@
 EXPORT const char* AMEDIAFORMAT_KEY_TRACK_ID = "track-id";
 EXPORT const char* AMEDIAFORMAT_KEY_TRACK_INDEX = "track-index";
 EXPORT const char* AMEDIAFORMAT_KEY_VALID_SAMPLES = "valid-samples";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_B_MAX = "video-qp-b-max";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_B_MIN = "video-qp-b-min";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_I_MAX = "video-qp-i-max";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_I_MIN = "video-qp-i-min";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_MAX = "video-qp-max";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_MIN = "video-qp-min";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_P_MAX = "video-qp-p-max";
+EXPORT const char* AMEDIAFORMAT_VIDEO_QP_P_MIN = "video-qp-p-min";
 EXPORT const char* AMEDIAFORMAT_KEY_WIDTH = "width";
 EXPORT const char* AMEDIAFORMAT_KEY_XMP_OFFSET = "xmp-offset";
 EXPORT const char* AMEDIAFORMAT_KEY_XMP_SIZE = "xmp-size";
diff --git a/media/ndk/include/media/NdkMediaFormat.h b/media/ndk/include/media/NdkMediaFormat.h
index eb6d510..476bbd9 100644
--- a/media/ndk/include/media/NdkMediaFormat.h
+++ b/media/ndk/include/media/NdkMediaFormat.h
@@ -308,6 +308,15 @@
 extern const char* AMEDIAFORMAT_KEY_XMP_OFFSET __INTRODUCED_IN(31);
 extern const char* AMEDIAFORMAT_KEY_XMP_SIZE __INTRODUCED_IN(31);
 
+extern const char* AMEDIAFORMAT_VIDEO_QP_B_MAX __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_B_MIN __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_I_MAX __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_I_MIN __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_MAX __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_MIN __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_P_MAX __INTRODUCED_IN(31);
+extern const char* AMEDIAFORMAT_VIDEO_QP_P_MIN __INTRODUCED_IN(31);
+
 __END_DECLS
 
 #endif // _NDK_MEDIA_FORMAT_H
diff --git a/services/audioflinger/AudioFlinger.cpp b/services/audioflinger/AudioFlinger.cpp
index dc2c171..ae9fc64 100644
--- a/services/audioflinger/AudioFlinger.cpp
+++ b/services/audioflinger/AudioFlinger.cpp
@@ -413,13 +413,18 @@
 /* static */
 int AudioFlinger::onExternalVibrationStart(const sp<os::ExternalVibration>& externalVibration) {
     sp<os::IExternalVibratorService> evs = getExternalVibratorService();
-    if (evs != 0) {
+    if (evs != nullptr) {
         int32_t ret;
         binder::Status status = evs->onExternalVibrationStart(*externalVibration, &ret);
         if (status.isOk()) {
+            ALOGD("%s, start external vibration with intensity as %d", __func__, ret);
             return ret;
         }
     }
+    ALOGD("%s, start external vibration with intensity as MUTE due to %s",
+            __func__,
+            evs == nullptr ? "external vibration service not found"
+                           : "error when querying intensity");
     return static_cast<int>(os::HapticScale::MUTE);
 }
 
diff --git a/services/audiopolicy/fuzzer/audiopolicy_fuzzer.cpp b/services/audiopolicy/fuzzer/audiopolicy_fuzzer.cpp
index c1f2aa8..692ce08 100644
--- a/services/audiopolicy/fuzzer/audiopolicy_fuzzer.cpp
+++ b/services/audiopolicy/fuzzer/audiopolicy_fuzzer.cpp
@@ -633,7 +633,9 @@
 }
 
 bool AudioPolicyManagerFuzzerDPPlaybackReRouting::initialize() {
-    AudioPolicyManagerFuzzerDynamicPolicy::initialize();
+    if (!AudioPolicyManagerFuzzerDynamicPolicy::initialize()) {
+        return false;
+    }
     mTracker.reset(new RecordingActivityTracker());
 
     mAudioConfig = AUDIO_CONFIG_INITIALIZER;
@@ -743,7 +745,9 @@
 }
 
 bool AudioPolicyManagerFuzzerDPMixRecordInjection::initialize() {
-    AudioPolicyManagerFuzzerDynamicPolicy::initialize();
+    if (!AudioPolicyManagerFuzzerDynamicPolicy::initialize()) {
+        return false;
+    }
 
     mTracker.reset(new RecordingActivityTracker());
 
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
index 04bc5f1..698692d 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
@@ -2184,7 +2184,9 @@
             status = BAD_VALUE;
             goto error;
         }
-        if (policyMix) {
+        if (device->type() == AUDIO_DEVICE_IN_ECHO_REFERENCE) {
+            *inputType = API_INPUT_MIX_CAPTURE;
+        } else if (policyMix) {
             ALOG_ASSERT(policyMix->mMixType == MIX_TYPE_RECORDERS, "Invalid Mix Type");
             // there is an external policy, but this input is attached to a mix of recorders,
             // meaning it receives audio injected into the framework, so the recorder doesn't
diff --git a/services/tuner/TunerDemux.cpp b/services/tuner/TunerDemux.cpp
index ba8d6a7..1122368 100644
--- a/services/tuner/TunerDemux.cpp
+++ b/services/tuner/TunerDemux.cpp
@@ -98,7 +98,7 @@
         return Status::fromServiceSpecificError(static_cast<int32_t>(status));
     }
 
-    *_aidl_return = ::ndk::SharedRefBase::make<TunerFilter>(filterSp, cbSp, type, subType);
+    *_aidl_return = ::ndk::SharedRefBase::make<TunerFilter>(filterSp, type, subType);
     return Status::ok();
 }
 
diff --git a/services/tuner/TunerFilter.cpp b/services/tuner/TunerFilter.cpp
index dc9d246..39a6723 100644
--- a/services/tuner/TunerFilter.cpp
+++ b/services/tuner/TunerFilter.cpp
@@ -39,10 +39,9 @@
 using namespace std;
 
 TunerFilter::TunerFilter(
-        sp<IFilter> filter, sp<IFilterCallback> callback, int mainType, int subType) {
+        sp<IFilter> filter, int mainType, int subType) {
     mFilter = filter;
     mFilter_1_1 = ::android::hardware::tv::tuner::V1_1::IFilter::castFrom(filter);
-    mFilterCallback = callback;
     mMainType = mainType;
     mSubType = subType;
 }
@@ -50,7 +49,6 @@
 TunerFilter::~TunerFilter() {
     mFilter = nullptr;
     mFilter_1_1 = nullptr;
-    mFilterCallback = nullptr;
 }
 
 Status TunerFilter::getQueueDesc(AidlMQDesc* _aidl_return) {
diff --git a/services/tuner/TunerFilter.h b/services/tuner/TunerFilter.h
index d12b7ac..ff4728c 100644
--- a/services/tuner/TunerFilter.h
+++ b/services/tuner/TunerFilter.h
@@ -92,7 +92,7 @@
 class TunerFilter : public BnTunerFilter {
 
 public:
-    TunerFilter(sp<IFilter> filter, sp<IFilterCallback> callback, int mainType, int subTyp);
+    TunerFilter(sp<IFilter> filter, int mainType, int subTyp);
     virtual ~TunerFilter();
     Status getId(int32_t* _aidl_return) override;
     Status getId64Bit(int64_t* _aidl_return) override;
@@ -181,7 +181,6 @@
 
     sp<IFilter> mFilter;
     sp<::android::hardware::tv::tuner::V1_1::IFilter> mFilter_1_1;
-    sp<IFilterCallback> mFilterCallback;
     int32_t mId;
     int64_t mId64Bit;
     int mMainType;
diff --git a/services/tuner/TunerService.cpp b/services/tuner/TunerService.cpp
index b80fd85..9624e27 100644
--- a/services/tuner/TunerService.cpp
+++ b/services/tuner/TunerService.cpp
@@ -49,7 +49,12 @@
 
 namespace android {
 
-TunerService::TunerService() {}
+TunerService::TunerService() {
+    ::ndk::SpAIBinder binder(AServiceManager_waitForService("tv_tuner_resource_mgr"));
+    mTunerResourceManager = ITunerResourceManager::fromBinder(binder);
+    updateTunerResources();
+}
+
 TunerService::~TunerService() {}
 
 binder_status_t TunerService::instantiate() {
@@ -282,19 +287,15 @@
     return Status::ok();
 }
 
-Status TunerService::updateTunerResources() {
-    if (!hasITuner()) {
-        return Status::fromServiceSpecificError(static_cast<int32_t>(Result::UNAVAILABLE));
+void TunerService::updateTunerResources() {
+    if (!hasITuner() || mTunerResourceManager == NULL) {
+        ALOGE("Failed to updateTunerResources");
+        return;
     }
 
-    // Connect with Tuner Resource Manager.
-    ::ndk::SpAIBinder binder(AServiceManager_getService("tv_tuner_resource_mgr"));
-    mTunerResourceManager = ITunerResourceManager::fromBinder(binder);
-
     updateFrontendResources();
     updateLnbResources();
     // TODO: update Demux, Descrambler.
-    return Status::ok();
 }
 
 Status TunerService::getTunerHalVersion(int* _aidl_return) {
diff --git a/services/tuner/TunerService.h b/services/tuner/TunerService.h
index cc65b39..0570681 100644
--- a/services/tuner/TunerService.h
+++ b/services/tuner/TunerService.h
@@ -113,7 +113,6 @@
     Status getDemuxCaps(TunerDemuxCapabilities* _aidl_return) override;
     Status openDescrambler(int32_t descramblerHandle,
             std::shared_ptr<ITunerDescrambler>* _aidl_return) override;
-    Status updateTunerResources() override;
     Status getTunerHalVersion(int* _aidl_return) override;
 
     // TODO: create a map between resource id and handles.
@@ -131,6 +130,7 @@
 private:
     bool hasITuner();
     bool hasITuner_1_1();
+    void updateTunerResources();
 
     void updateFrontendResources();
     void updateLnbResources();
diff --git a/services/tuner/aidl/android/media/tv/tuner/ITunerService.aidl b/services/tuner/aidl/android/media/tv/tuner/ITunerService.aidl
index f1651b9..755b152 100644
--- a/services/tuner/aidl/android/media/tv/tuner/ITunerService.aidl
+++ b/services/tuner/aidl/android/media/tv/tuner/ITunerService.aidl
@@ -97,12 +97,6 @@
     ITunerDescrambler openDescrambler(in int descramblerHandle);
 
     /**
-     * Update Tuner Resources in TunerResourceManager.
-     */
-    // TODO: b/178124017 update TRM in TunerService independently.
-    void updateTunerResources();
-
-    /**
      * Get an integer that carries the Tuner HIDL version. The high 16 bits are the
      * major version number while the low 16 bits are the minor version. Default
      * value is unknown version 0.
