diff --git a/audio/aidl/vts/Android.bp b/audio/aidl/vts/Android.bp
index 63fc415..8de1d79 100644
--- a/audio/aidl/vts/Android.bp
+++ b/audio/aidl/vts/Android.bp
@@ -60,6 +60,7 @@
         "android.hardware.common-V2-ndk",
         "android.hardware.common.fmq-V1-ndk",
     ],
+    header_libs: ["libaudioaidl_headers"],
     cflags: [
         "-Wall",
         "-Wextra",
@@ -75,6 +76,7 @@
 cc_test {
     name: "VtsHalAudioEffectTargetTest",
     defaults: [
+        "latest_android_hardware_audio_common_ndk_static",
         "latest_android_media_audio_common_types_ndk_static",
         "VtsHalTargetTestDefaults",
         "use_libaidlvintf_gtest_helper_static",
@@ -84,12 +86,49 @@
     ],
     shared_libs: [
         "libbinder_ndk",
+        "libfmq",
     ],
     static_libs: [
         "android.hardware.audio.effect-V1-ndk",
         "android.hardware.common-V2-ndk",
         "android.hardware.common.fmq-V1-ndk",
+        "libaudioaidlcommon",
     ],
+    header_libs: ["libaudioaidl_headers"],
+    cflags: [
+        "-Wall",
+        "-Wextra",
+        "-Werror",
+        "-Wthread-safety",
+    ],
+    test_suites: [
+        "general-tests",
+        "vts",
+    ],
+}
+
+cc_test {
+    name: "VtsHalEqualizerTargetTest",
+    defaults: [
+        "latest_android_hardware_audio_common_ndk_static",
+        "latest_android_media_audio_common_types_ndk_static",
+        "VtsHalTargetTestDefaults",
+        "use_libaidlvintf_gtest_helper_static",
+    ],
+    srcs: [
+        "VtsHalEqualizerTargetTest.cpp",
+    ],
+    shared_libs: [
+        "libbinder_ndk",
+        "libfmq",
+    ],
+    static_libs: [
+        "android.hardware.audio.effect-V1-ndk",
+        "android.hardware.common-V2-ndk",
+        "android.hardware.common.fmq-V1-ndk",
+        "libaudioaidlcommon",
+    ],
+    header_libs: ["libaudioaidl_headers"],
     cflags: [
         "-Wall",
         "-Wextra",
diff --git a/audio/aidl/vts/EffectFactoryHelper.h b/audio/aidl/vts/EffectFactoryHelper.h
index cf94e58..63efae0 100644
--- a/audio/aidl/vts/EffectFactoryHelper.h
+++ b/audio/aidl/vts/EffectFactoryHelper.h
@@ -24,13 +24,14 @@
 #include <android/binder_auto_utils.h>
 
 #include "TestUtils.h"
+#include "effect-impl/EffectUUID.h"
 
 using namespace android;
 
 using aidl::android::hardware::audio::effect::Descriptor;
+using aidl::android::hardware::audio::effect::EffectNullUuid;
 using aidl::android::hardware::audio::effect::IEffect;
 using aidl::android::hardware::audio::effect::IFactory;
-using aidl::android::hardware::audio::effect::Parameter;
 using aidl::android::hardware::audio::effect::Processing;
 using aidl::android::media::audio::common::AudioUuid;
 
@@ -69,7 +70,6 @@
     }
 
     void CreateEffects() {
-        ASSERT_NE(mEffectFactory, nullptr);
         for (const auto& id : mIds) {
             std::shared_ptr<IEffect> effect;
             EXPECT_IS_OK(mEffectFactory->createEffect(id.uuid, &effect));
@@ -80,6 +80,26 @@
         }
     }
 
+    void QueryAndCreateEffects(const AudioUuid& type = EffectNullUuid) {
+        std::vector<Descriptor::Identity> ids;
+        ASSERT_NE(mEffectFactory, nullptr);
+
+        if (type == EffectNullUuid) {
+            EXPECT_IS_OK(mEffectFactory->queryEffects(std::nullopt, std::nullopt, &ids));
+        } else {
+            EXPECT_IS_OK(mEffectFactory->queryEffects(type, std::nullopt, &ids));
+        }
+        for (const auto& id : ids) {
+            ASSERT_EQ(id.type, type);
+            std::shared_ptr<IEffect> effect;
+            EXPECT_IS_OK(mEffectFactory->createEffect(id.uuid, &effect));
+            EXPECT_NE(effect, nullptr) << id.toString();
+            if (effect) {
+                mEffectIdMap[effect] = id;
+            }
+        }
+    }
+
     void CreateEffectsAndExpect(
             const std::vector<std::pair<Descriptor::Identity, binder_exception_t>>& uuid_status) {
         ASSERT_NE(mEffectFactory, nullptr);
@@ -126,8 +146,10 @@
 
     std::shared_ptr<IFactory> GetFactory() { return mEffectFactory; }
     const std::vector<Descriptor::Identity>& GetEffectIds() { return mIds; }
-    const std::vector<Descriptor::Identity>& GetCompleteEffectIdList() { return mCompleteIds; }
-    const std::map<std::shared_ptr<IEffect>, Descriptor::Identity>& GetEffectMap() {
+    const std::vector<Descriptor::Identity>& GetCompleteEffectIdList() const {
+        return mCompleteIds;
+    }
+    const std::map<std::shared_ptr<IEffect>, Descriptor::Identity>& GetEffectMap() const {
         return mEffectIdMap;
     }
     void ClearEffectMap() { mEffectIdMap.clear(); }
diff --git a/audio/aidl/vts/EffectHelper.h b/audio/aidl/vts/EffectHelper.h
new file mode 100644
index 0000000..c58ed13
--- /dev/null
+++ b/audio/aidl/vts/EffectHelper.h
@@ -0,0 +1,310 @@
+/*
+ * Copyright (C) 2022 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.
+ */
+
+#pragma once
+
+#include <memory>
+#include <string>
+#include <unordered_map>
+#include <vector>
+
+#include <aidl/android/hardware/audio/effect/IEffect.h>
+#include <aidl/android/hardware/audio/effect/IFactory.h>
+#include <aidl/android/media/audio/common/AudioChannelLayout.h>
+#include <aidl/android/media/audio/common/AudioDeviceType.h>
+#include <android/binder_auto_utils.h>
+#include <fmq/AidlMessageQueue.h>
+
+#include "AudioHalBinderServiceUtil.h"
+#include "EffectFactoryHelper.h"
+#include "TestUtils.h"
+
+using namespace android;
+using aidl::android::hardware::audio::effect::CommandId;
+using aidl::android::hardware::audio::effect::Descriptor;
+using aidl::android::hardware::audio::effect::EffectNullUuid;
+using aidl::android::hardware::audio::effect::EffectZeroUuid;
+using aidl::android::hardware::audio::effect::IEffect;
+using aidl::android::hardware::audio::effect::Parameter;
+using aidl::android::hardware::audio::effect::State;
+using aidl::android::hardware::common::fmq::SynchronizedReadWrite;
+using aidl::android::media::audio::common::AudioChannelLayout;
+using aidl::android::media::audio::common::AudioDeviceType;
+using aidl::android::media::audio::common::AudioFormatDescription;
+using aidl::android::media::audio::common::AudioFormatType;
+using aidl::android::media::audio::common::AudioUuid;
+using aidl::android::media::audio::common::PcmType;
+
+const AudioFormatDescription DefaultFormat = {
+        .type = AudioFormatType::PCM, .pcm = PcmType::INT_16_BIT, .encoding = ""};
+
+class EffectHelper {
+  public:
+    explicit EffectHelper(const std::string& name) : mFactoryHelper(EffectFactoryHelper(name)) {
+        mFactoryHelper.ConnectToFactoryService();
+    }
+
+    void OpenEffects(const AudioUuid& type = EffectNullUuid) {
+        auto open = [&](const std::shared_ptr<IEffect>& effect) {
+            IEffect::OpenEffectReturn ret;
+            EXPECT_IS_OK(effect->open(mCommon, mSpecific, &ret));
+            EffectParam params;
+            params.statusMQ = std::make_unique<StatusMQ>(ret.statusMQ);
+            params.inputMQ = std::make_unique<DataMQ>(ret.inputDataMQ);
+            params.outputMQ = std::make_unique<DataMQ>(ret.outputDataMQ);
+            mEffectParams.push_back(std::move(params));
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(open, type));
+    }
+
+    void CloseEffects(const binder_status_t status = EX_NONE) {
+        auto close = [&](const std::shared_ptr<IEffect>& effect) {
+            EXPECT_STATUS(status, effect->close());
+        };
+
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(close));
+    }
+
+    void CreateEffects(const int n = 1) {
+        for (int i = 0; i < n; i++) {
+            ASSERT_NO_FATAL_FAILURE(mFactoryHelper.QueryAndCreateAllEffects());
+        }
+    }
+
+    void CreateEffectsWithUUID(const AudioUuid& type = EffectNullUuid) {
+        ASSERT_NO_FATAL_FAILURE(mFactoryHelper.QueryAndCreateEffects(type));
+    }
+
+    void QueryEffects() { ASSERT_NO_FATAL_FAILURE(mFactoryHelper.QueryAndCreateAllEffects()); }
+
+    void DestroyEffects(const binder_status_t status = EX_NONE, const int remaining = 0) {
+        ASSERT_NO_FATAL_FAILURE(mFactoryHelper.DestroyEffects(status, remaining));
+        mEffectDescriptors.clear();
+    }
+
+    void GetEffectDescriptors() {
+        auto get = [&](const std::shared_ptr<IEffect>& effect) {
+            Descriptor desc;
+            EXPECT_IS_OK(effect->getDescriptor(&desc));
+            mEffectDescriptors.push_back(std::move(desc));
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(get));
+    }
+
+    void CommandEffects(CommandId command) {
+        auto close = [&](const std::shared_ptr<IEffect>& effect) {
+            EXPECT_IS_OK(effect->command(command));
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(close));
+    }
+
+    void CommandEffectsExpectStatus(CommandId command, const binder_status_t status) {
+        auto func = [&](const std::shared_ptr<IEffect>& effect) {
+            EXPECT_STATUS(status, effect->command(command));
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(func));
+    }
+
+    void ExpectState(State expected) {
+        auto get = [&](const std::shared_ptr<IEffect>& effect) {
+            State state = State::INIT;
+            EXPECT_IS_OK(effect->getState(&state));
+            EXPECT_EQ(expected, state);
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(get));
+    }
+
+    void SetParameter() {
+        auto func = [&](const std::shared_ptr<IEffect>& effect) {
+            Parameter param;
+            param.set<Parameter::common>(mCommon);
+            EXPECT_IS_OK(effect->setParameter(param));
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(func));
+    }
+
+    void VerifyParameters() {
+        auto func = [&](const std::shared_ptr<IEffect>& effect) {
+            Parameter paramCommonGet = Parameter(), paramCommonExpect = Parameter();
+            Parameter::Id id;
+            id.set<Parameter::Id::commonTag>(0);
+            paramCommonExpect.set<Parameter::common>(mCommon);
+            EXPECT_IS_OK(effect->getParameter(id, &paramCommonGet));
+            EXPECT_EQ(paramCommonExpect, paramCommonGet)
+                    << paramCommonExpect.toString() << " vs " << paramCommonGet.toString();
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(func));
+    }
+
+    void QueryEffects(const std::optional<AudioUuid>& in_type,
+                      const std::optional<AudioUuid>& in_instance,
+                      std::vector<Descriptor::Identity>* _aidl_return) {
+        mFactoryHelper.QueryEffects(in_type, in_instance, _aidl_return);
+    }
+
+    template <typename Functor>
+    void ForEachEffect(Functor functor, const std::optional<AudioUuid>& type = EffectNullUuid) {
+        auto effectMap = mFactoryHelper.GetEffectMap();
+        for (const auto& it : effectMap) {
+            SCOPED_TRACE(it.second.toString());
+            if (type != EffectNullUuid && it.second.type != type) continue;
+            functor(it.first);
+        }
+    }
+
+    template <typename Functor>
+    void ForEachDescriptor(Functor functor) {
+        for (size_t i = 0; i < mEffectDescriptors.size(); i++) {
+            SCOPED_TRACE(mEffectDescriptors[i].toString());
+            functor(i, mEffectDescriptors[i]);
+        }
+    }
+
+    static const size_t mWriteMQSize = 0x400;
+
+    enum class IO : char { INPUT = 0, OUTPUT = 1, INOUT = 2 };
+
+    void initParamCommonFormat(IO io = IO::INOUT,
+                               const AudioFormatDescription& format = DefaultFormat) {
+        if (io == IO::INPUT || io == IO::INOUT) {
+            mCommon.input.base.format = format;
+        }
+        if (io == IO::OUTPUT || io == IO::INOUT) {
+            mCommon.output.base.format = format;
+        }
+    }
+
+    void initParamCommonSampleRate(IO io = IO::INOUT, const int& sampleRate = 48000) {
+        if (io == IO::INPUT || io == IO::INOUT) {
+            mCommon.input.base.sampleRate = sampleRate;
+        }
+        if (io == IO::OUTPUT || io == IO::INOUT) {
+            mCommon.output.base.sampleRate = sampleRate;
+        }
+    }
+
+    void initParamCommonFrameCount(IO io = IO::INOUT, const long& frameCount = 48000) {
+        if (io == IO::INPUT || io == IO::INOUT) {
+            mCommon.input.frameCount = frameCount;
+        }
+        if (io == IO::OUTPUT || io == IO::INOUT) {
+            mCommon.output.frameCount = frameCount;
+        }
+    }
+    void initParamCommon(int session = -1, int ioHandle = -1, int iSampleRate = 48000,
+                         int oSampleRate = 48000, long iFrameCount = 0x100,
+                         long oFrameCount = 0x100) {
+        mCommon.session = session;
+        mCommon.ioHandle = ioHandle;
+
+        auto& input = mCommon.input;
+        auto& output = mCommon.output;
+        input.base.sampleRate = iSampleRate;
+        input.base.channelMask = mInputChannelLayout;
+        input.frameCount = iFrameCount;
+        output.base.sampleRate = oSampleRate;
+        output.base.channelMask = mOutputChannelLayout;
+        output.frameCount = oFrameCount;
+        inputFrameSize = android::hardware::audio::common::getFrameSizeInBytes(
+                input.base.format, input.base.channelMask);
+        outputFrameSize = android::hardware::audio::common::getFrameSizeInBytes(
+                output.base.format, output.base.channelMask);
+    }
+
+    void setSpecific(Parameter::Specific& specific) { mSpecific = specific; }
+
+    // usually this function only call once.
+    void PrepareInputData(size_t s = mWriteMQSize) {
+        size_t maxInputSize = s;
+        for (auto& it : mEffectParams) {
+            auto& mq = it.inputMQ;
+            EXPECT_NE(nullptr, mq);
+            EXPECT_TRUE(mq->isValid());
+            const size_t bytesToWrite = mq->availableToWrite();
+            EXPECT_EQ(inputFrameSize * mCommon.input.frameCount, bytesToWrite);
+            EXPECT_NE(0UL, bytesToWrite);
+            EXPECT_TRUE(s <= bytesToWrite);
+            maxInputSize = std::max(maxInputSize, bytesToWrite);
+        }
+        mInputBuffer.resize(maxInputSize);
+        std::fill(mInputBuffer.begin(), mInputBuffer.end(), 0x5a);
+    }
+
+    void writeToFmq(size_t s = mWriteMQSize) {
+        for (auto& it : mEffectParams) {
+            auto& mq = it.inputMQ;
+            EXPECT_NE(nullptr, mq);
+            const size_t bytesToWrite = mq->availableToWrite();
+            EXPECT_NE(0Ul, bytesToWrite);
+            EXPECT_TRUE(s <= bytesToWrite);
+            EXPECT_TRUE(mq->write(mInputBuffer.data(), s));
+        }
+    }
+
+    void readFromFmq(size_t expectSize = mWriteMQSize) {
+        for (auto& it : mEffectParams) {
+            IEffect::Status status{};
+            auto& statusMq = it.statusMQ;
+            EXPECT_NE(nullptr, statusMq);
+            EXPECT_TRUE(statusMq->readBlocking(&status, 1));
+            EXPECT_EQ(STATUS_OK, status.status);
+            EXPECT_EQ(expectSize, (unsigned)status.fmqByteProduced);
+
+            auto& outputMq = it.outputMQ;
+            EXPECT_NE(nullptr, outputMq);
+            EXPECT_EQ(expectSize, outputMq->availableToRead());
+        }
+    }
+
+    void setInputChannelLayout(AudioChannelLayout input) { mInputChannelLayout = input; }
+    void setOutputChannelLayout(AudioChannelLayout output) { mOutputChannelLayout = output; }
+    const std::vector<Descriptor::Identity>& GetCompleteEffectIdList() const {
+        return mFactoryHelper.GetCompleteEffectIdList();
+    }
+    const std::vector<Descriptor>& getDescriptorVec() const { return mEffectDescriptors; }
+
+  private:
+    EffectFactoryHelper mFactoryHelper;
+
+    AudioChannelLayout mInputChannelLayout =
+            AudioChannelLayout::make<AudioChannelLayout::layoutMask>(
+                    AudioChannelLayout::LAYOUT_STEREO);
+    AudioChannelLayout mOutputChannelLayout =
+            AudioChannelLayout::make<AudioChannelLayout::layoutMask>(
+                    AudioChannelLayout::LAYOUT_STEREO);
+
+    Parameter::Common mCommon;
+    Parameter::Specific mSpecific;
+
+    size_t inputFrameSize, outputFrameSize;
+    std::vector<int8_t> mInputBuffer;  // reuse same buffer for all effects testing
+
+    typedef ::android::AidlMessageQueue<
+            IEffect::Status, ::aidl::android::hardware::common::fmq::SynchronizedReadWrite>
+            StatusMQ;
+    typedef ::android::AidlMessageQueue<
+            int8_t, ::aidl::android::hardware::common::fmq::SynchronizedReadWrite>
+            DataMQ;
+
+    class EffectParam {
+      public:
+        std::unique_ptr<StatusMQ> statusMQ;
+        std::unique_ptr<DataMQ> inputMQ;
+        std::unique_ptr<DataMQ> outputMQ;
+    };
+    std::vector<EffectParam> mEffectParams;
+    std::vector<Descriptor> mEffectDescriptors;
+};
diff --git a/audio/aidl/vts/VtsHalAudioEffectFactoryTargetTest.cpp b/audio/aidl/vts/VtsHalAudioEffectFactoryTargetTest.cpp
index 454ce29..da8ca37 100644
--- a/audio/aidl/vts/VtsHalAudioEffectFactoryTargetTest.cpp
+++ b/audio/aidl/vts/VtsHalAudioEffectFactoryTargetTest.cpp
@@ -37,6 +37,8 @@
 using namespace android;
 
 using aidl::android::hardware::audio::effect::Descriptor;
+using aidl::android::hardware::audio::effect::EffectNullUuid;
+using aidl::android::hardware::audio::effect::EffectZeroUuid;
 using aidl::android::hardware::audio::effect::IFactory;
 using aidl::android::hardware::audio::effect::Processing;
 using aidl::android::media::audio::common::AudioUuid;
@@ -50,17 +52,8 @@
 
     EffectFactoryHelper mFactory = EffectFactoryHelper(GetParam());
 
-    // TODO: these UUID can get from config file
-    // ec7178ec-e5e1-4432-a3f4-4657e6795210
-    const AudioUuid nullUuid = {static_cast<int32_t>(0xec7178ec),
-                                0xe5e1,
-                                0x4432,
-                                0xa3f4,
-                                {0x46, 0x57, 0xe6, 0x79, 0x52, 0x10}};
-    const AudioUuid zeroUuid = {
-            static_cast<int32_t>(0x0), 0x0, 0x0, 0x0, {0x0, 0x0, 0x0, 0x0, 0x0, 0x0}};
-    const Descriptor::Identity nullDesc = {.uuid = nullUuid};
-    const Descriptor::Identity zeroDesc = {.uuid = zeroUuid};
+    const Descriptor::Identity nullDesc = {.uuid = EffectNullUuid};
+    const Descriptor::Identity zeroDesc = {.uuid = EffectZeroUuid};
 };
 
 TEST_P(EffectFactoryTest, SetupAndTearDown) {
@@ -82,20 +75,20 @@
     mFactory.QueryEffects(std::nullopt, std::nullopt, &descriptors);
     // TODO: Factory eventually need to return the full list of MUST supported AOSP effects.
     for (auto& desc : descriptors) {
-        EXPECT_NE(desc.type, zeroUuid);
-        EXPECT_NE(desc.uuid, zeroUuid);
+        EXPECT_NE(desc.type, EffectNullUuid);
+        EXPECT_NE(desc.uuid, EffectNullUuid);
     }
 }
 
 TEST_P(EffectFactoryTest, QueriedDescriptorNotExistType) {
     std::vector<Descriptor::Identity> descriptors;
-    mFactory.QueryEffects(nullUuid, std::nullopt, &descriptors);
+    mFactory.QueryEffects(EffectNullUuid, std::nullopt, &descriptors);
     EXPECT_EQ(descriptors.size(), 0UL);
 }
 
 TEST_P(EffectFactoryTest, QueriedDescriptorNotExistInstance) {
     std::vector<Descriptor::Identity> descriptors;
-    mFactory.QueryEffects(std::nullopt, nullUuid, &descriptors);
+    mFactory.QueryEffects(std::nullopt, EffectNullUuid, &descriptors);
     EXPECT_EQ(descriptors.size(), 0UL);
 }
 
diff --git a/audio/aidl/vts/VtsHalAudioEffectTargetTest.cpp b/audio/aidl/vts/VtsHalAudioEffectTargetTest.cpp
index 23b20bd..7ed1f01 100644
--- a/audio/aidl/vts/VtsHalAudioEffectTargetTest.cpp
+++ b/audio/aidl/vts/VtsHalAudioEffectTargetTest.cpp
@@ -14,14 +14,14 @@
  * limitations under the License.
  */
 
+#define LOG_TAG "VtsHalAudioEffectTargetTest"
+
 #include <memory>
 #include <string>
 #include <unordered_map>
 #include <unordered_set>
 #include <vector>
 
-#define LOG_TAG "VtsHalAudioEffect"
-
 #include <aidl/Gtest.h>
 #include <aidl/Vintf.h>
 #include <android-base/logging.h>
@@ -30,13 +30,13 @@
 #include <android/binder_manager.h>
 #include <android/binder_process.h>
 
+#include <Utils.h>
 #include <aidl/android/hardware/audio/effect/IEffect.h>
 #include <aidl/android/hardware/audio/effect/IFactory.h>
-#include <aidl/android/media/audio/common/AudioChannelLayout.h>
 #include <aidl/android/media/audio/common/AudioDeviceType.h>
 
 #include "AudioHalBinderServiceUtil.h"
-#include "EffectFactoryHelper.h"
+#include "EffectHelper.h"
 #include "TestUtils.h"
 
 using namespace android;
@@ -49,201 +49,72 @@
 using aidl::android::hardware::audio::effect::IFactory;
 using aidl::android::hardware::audio::effect::Parameter;
 using aidl::android::hardware::audio::effect::State;
-using aidl::android::media::audio::common::AudioChannelLayout;
 using aidl::android::media::audio::common::AudioDeviceType;
 
-class AudioEffect : public testing::TestWithParam<std::string> {
+class AudioEffectTest : public testing::TestWithParam<std::string>, public EffectHelper {
   public:
+    AudioEffectTest() : EffectHelper(GetParam()) {}
+
     void SetUp() override {
-        ASSERT_NO_FATAL_FAILURE(mFactoryHelper.ConnectToFactoryService());
         CreateEffects();
+        initParamCommonFormat();
         initParamCommon();
-        initParamSpecific();
+        // initParamSpecific();
     }
 
     void TearDown() override {
         CloseEffects();
         DestroyEffects();
     }
-
-    void OpenEffects() {
-        auto open = [&](const std::shared_ptr<IEffect>& effect) {
-            IEffect::OpenEffectReturn ret;
-            EXPECT_IS_OK(effect->open(mCommon, mSpecific, &ret));
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(open));
-    }
-
-    void CloseEffects(const binder_status_t status = EX_NONE) {
-        auto close = [&](const std::shared_ptr<IEffect>& effect) {
-            EXPECT_STATUS(status, effect->close());
-        };
-
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(close));
-    }
-
-    void CreateEffects(const int n = 1) {
-        for (int i = 0; i < n; i++) {
-            ASSERT_NO_FATAL_FAILURE(mFactoryHelper.QueryAndCreateAllEffects());
-        }
-    }
-
-    void DestroyEffects(const binder_status_t status = EX_NONE, const int remaining = 0) {
-        ASSERT_NO_FATAL_FAILURE(mFactoryHelper.DestroyEffects(status, remaining));
-    }
-
-    void GetEffectDescriptors() {
-        auto get = [](const std::shared_ptr<IEffect>& effect) {
-            Descriptor desc;
-            EXPECT_IS_OK(effect->getDescriptor(&desc));
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(get));
-    }
-
-    void CommandEffects(CommandId command) {
-        auto close = [&](const std::shared_ptr<IEffect>& effect) {
-            EXPECT_IS_OK(effect->command(command));
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(close));
-    }
-
-    void CommandEffectsExpectStatus(CommandId command, const binder_status_t status) {
-        auto func = [&](const std::shared_ptr<IEffect>& effect) {
-            EXPECT_STATUS(status, effect->command(command));
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(func));
-    }
-
-    void ExpectState(State expected) {
-        auto get = [&](const std::shared_ptr<IEffect>& effect) {
-            State state = State::INIT;
-            EXPECT_IS_OK(effect->getState(&state));
-            EXPECT_EQ(expected, state);
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(get));
-    }
-
-    void SetParameter() {
-        auto func = [&](const std::shared_ptr<IEffect>& effect) {
-            Parameter param;
-            param.set<Parameter::common>(mCommon);
-            EXPECT_IS_OK(effect->setParameter(param));
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(func));
-    }
-
-    void VerifyParameters() {
-        auto func = [&](const std::shared_ptr<IEffect>& effect) {
-            Parameter paramCommonGet = Parameter(), paramCommonExpect = Parameter();
-            Parameter::Id id;
-            id.set<Parameter::Id::commonTag>(0);
-            paramCommonExpect.set<Parameter::common>(mCommon);
-            EXPECT_IS_OK(effect->getParameter(id, &paramCommonGet));
-            EXPECT_EQ(paramCommonExpect, paramCommonGet)
-                    << paramCommonExpect.toString() << " vs " << paramCommonGet.toString();
-        };
-        EXPECT_NO_FATAL_FAILURE(ForEachEffect(func));
-    }
-
-    template <typename Functor>
-    void ForEachEffect(Functor functor) {
-        auto effectMap = mFactoryHelper.GetEffectMap();
-        for (const auto& it : effectMap) {
-            SCOPED_TRACE(it.second.toString());
-            functor(it.first);
-        }
-    }
-
-    void initParamCommon(int session = -1, int ioHandle = -1,
-                         AudioDeviceType deviceType = AudioDeviceType::NONE,
-                         int iSampleRate = 48000, int oSampleRate = 48000, long iFrameCount = 0x100,
-                         long oFrameCount = 0x100) {
-        mCommon.session = session;
-        mCommon.ioHandle = ioHandle;
-        mCommon.device.type = deviceType;
-        mCommon.input.base.sampleRate = iSampleRate;
-        mCommon.input.base.channelMask = mInputChannelLayout;
-        mCommon.input.frameCount = iFrameCount;
-        mCommon.output.base.sampleRate = oSampleRate;
-        mCommon.output.base.channelMask = mOutputChannelLayout;
-        mCommon.output.frameCount = oFrameCount;
-    }
-
-    void initParamSpecific(Parameter::Specific::Tag tag = Parameter::Specific::equalizer) {
-        switch (tag) {
-            case Parameter::Specific::equalizer:
-                mSpecific.set<Parameter::Specific::equalizer>();
-                break;
-            default:
-                return;
-        }
-    }
-
-    void setInputChannelLayout(AudioChannelLayout input) { mInputChannelLayout = input; }
-    void setOutputChannelLayout(AudioChannelLayout output) { mOutputChannelLayout = output; }
-
-    EffectFactoryHelper mFactoryHelper = EffectFactoryHelper(GetParam());
-
-  private:
-    AudioChannelLayout mInputChannelLayout =
-            AudioChannelLayout::make<AudioChannelLayout::layoutMask>(
-                    AudioChannelLayout::LAYOUT_STEREO);
-    AudioChannelLayout mOutputChannelLayout =
-            AudioChannelLayout::make<AudioChannelLayout::layoutMask>(
-                    AudioChannelLayout::LAYOUT_STEREO);
-
-    Parameter::Common mCommon;
-    Parameter::Specific mSpecific;
-    static IEffect::OpenEffectReturn mOpenReturn;
 };
 
-TEST_P(AudioEffect, OpenEffectTest) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
+TEST_P(AudioEffectTest, OpenEffectTest) {
+    OpenEffects();
 }
 
-TEST_P(AudioEffect, OpenAndCloseEffect) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+TEST_P(AudioEffectTest, OpenAndCloseEffect) {
+    OpenEffects();
+    CloseEffects();
 }
 
-TEST_P(AudioEffect, CloseUnopenedEffectTest) {
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+TEST_P(AudioEffectTest, CloseUnopenedEffectTest) {
+    CloseEffects();
 }
 
-TEST_P(AudioEffect, DoubleOpenCloseEffects) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+TEST_P(AudioEffectTest, DoubleOpenCloseEffects) {
+    OpenEffects();
+    CloseEffects();
+    OpenEffects();
+    CloseEffects();
 
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    OpenEffects();
+    OpenEffects();
+    CloseEffects();
 
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    OpenEffects();
+    CloseEffects();
+    CloseEffects();
 }
 
-TEST_P(AudioEffect, GetDescriptors) {
-    EXPECT_NO_FATAL_FAILURE(GetEffectDescriptors());
+TEST_P(AudioEffectTest, GetDescriptors) {
+    GetEffectDescriptors();
 }
 
-TEST_P(AudioEffect, DescriptorIdExistAndUnique) {
+TEST_P(AudioEffectTest, DescriptorIdExistAndUnique) {
     auto checker = [&](const std::shared_ptr<IEffect>& effect) {
         Descriptor desc;
         std::vector<Descriptor::Identity> idList;
         EXPECT_IS_OK(effect->getDescriptor(&desc));
-        mFactoryHelper.QueryEffects(desc.common.id.type, desc.common.id.uuid, &idList);
+        QueryEffects(desc.common.id.type, desc.common.id.uuid, &idList);
         EXPECT_EQ(idList.size(), 1UL);
     };
-    EXPECT_NO_FATAL_FAILURE(ForEachEffect(checker));
+    ForEachEffect(checker);
 
     // Check unique with a set
     auto stringHash = [](const Descriptor::Identity& id) {
         return std::hash<std::string>()(id.toString());
     };
-    auto vec = mFactoryHelper.GetCompleteEffectIdList();
+    auto vec = GetCompleteEffectIdList();
     std::unordered_set<Descriptor::Identity, decltype(stringHash)> idSet(0, stringHash);
     for (auto it : vec) {
         EXPECT_EQ(idSet.count(it), 0UL);
@@ -253,218 +124,235 @@
 
 /// State testing.
 // An effect instance is in INIT state by default after it was created.
-TEST_P(AudioEffect, InitStateAfterCreation) {
+TEST_P(AudioEffectTest, InitStateAfterCreation) {
     ExpectState(State::INIT);
 }
 
 // An effect instance transfer to INIT state after it was open successfully with IEffect.open().
-TEST_P(AudioEffect, IdleStateAfterOpen) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
+TEST_P(AudioEffectTest, IdleStateAfterOpen) {
+    OpenEffects();
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // An effect instance is in PROCESSING state after it receive an START command.
-TEST_P(AudioEffect, ProcessingStateAfterStart) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, ProcessingStateAfterStart) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CommandEffects(CommandId::STOP);
+    CloseEffects();
 }
 
 // An effect instance transfer to IDLE state after Command.Id.STOP in PROCESSING state.
-TEST_P(AudioEffect, IdleStateAfterStop) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, IdleStateAfterStop) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // An effect instance transfer to IDLE state after Command.Id.RESET in PROCESSING state.
-TEST_P(AudioEffect, IdleStateAfterReset) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, IdleStateAfterReset) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::RESET));
+    CommandEffects(CommandId::RESET);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // An effect instance transfer to INIT if instance receive a close() call.
-TEST_P(AudioEffect, InitStateAfterClose) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, InitStateAfterClose) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
     ExpectState(State::INIT);
 }
 
 // An effect instance shouldn't accept any command before open.
-TEST_P(AudioEffect, NoCommandAcceptedBeforeOpen) {
+TEST_P(AudioEffectTest, NoCommandAcceptedBeforeOpen) {
     ExpectState(State::INIT);
-    EXPECT_NO_FATAL_FAILURE(CommandEffectsExpectStatus(CommandId::START, EX_ILLEGAL_STATE));
-    EXPECT_NO_FATAL_FAILURE(CommandEffectsExpectStatus(CommandId::STOP, EX_ILLEGAL_STATE));
-    EXPECT_NO_FATAL_FAILURE(CommandEffectsExpectStatus(CommandId::RESET, EX_ILLEGAL_STATE));
+    CommandEffectsExpectStatus(CommandId::START, EX_ILLEGAL_STATE);
+    CommandEffectsExpectStatus(CommandId::STOP, EX_ILLEGAL_STATE);
+    CommandEffectsExpectStatus(CommandId::RESET, EX_ILLEGAL_STATE);
     ExpectState(State::INIT);
 }
 
 // No-op when receive STOP command in IDLE state.
-TEST_P(AudioEffect, StopCommandInIdleStateNoOp) {
+TEST_P(AudioEffectTest, StopCommandInIdleStateNoOp) {
     ExpectState(State::INIT);
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
+    OpenEffects();
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // No-op when receive STOP command in IDLE state.
-TEST_P(AudioEffect, ResetCommandInIdleStateNoOp) {
+TEST_P(AudioEffectTest, ResetCommandInIdleStateNoOp) {
     ExpectState(State::INIT);
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
+    OpenEffects();
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::RESET));
+    CommandEffects(CommandId::RESET);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // Repeat START and STOP command.
-TEST_P(AudioEffect, RepeatStartAndStop) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, RepeatStartAndStop) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // Repeat START and RESET command.
-TEST_P(AudioEffect, RepeatStartAndReset) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, RepeatStartAndReset) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::RESET));
+    CommandEffects(CommandId::RESET);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::RESET));
+    CommandEffects(CommandId::RESET);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // Repeat START and STOP command, try to close at PROCESSING state.
-TEST_P(AudioEffect, CloseProcessingStateEffects) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, CloseProcessingStateEffects) {
+    OpenEffects();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects(EX_ILLEGAL_STATE));
+    CloseEffects(EX_ILLEGAL_STATE);
     // cleanup
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
 }
 
 // Expect EX_ILLEGAL_STATE if the effect instance is not in a proper state to be destroyed.
-TEST_P(AudioEffect, DestroyOpenEffects) {
+TEST_P(AudioEffectTest, DestroyOpenEffects) {
     // cleanup all effects.
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
-    ASSERT_NO_FATAL_FAILURE(DestroyEffects());
+    CloseEffects();
+    DestroyEffects();
 
     // open effects, destroy without close, expect to get EX_ILLEGAL_STATE status.
-    EXPECT_NO_FATAL_FAILURE(CreateEffects());
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(DestroyEffects(EX_ILLEGAL_STATE, 1));
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CreateEffects();
+    OpenEffects();
+    DestroyEffects(EX_ILLEGAL_STATE, 1);
+    CloseEffects();
 }
 
 /// Parameter testing.
 // Verify parameters pass in open can be successfully get.
-TEST_P(AudioEffect, VerifyParametersAfterOpen) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+TEST_P(AudioEffectTest, VerifyParametersAfterOpen) {
+    OpenEffects();
+    VerifyParameters();
+    CloseEffects();
 }
 
 // Verify parameters pass in set can be successfully get.
-TEST_P(AudioEffect, SetAndGetParameter) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    initParamCommon(1 /* session */, 1 /* ioHandle */, AudioDeviceType::IN_DEFAULT /* deviceType */,
-                    44100 /* iSampleRate */, 44100 /* oSampleRate */);
-    EXPECT_NO_FATAL_FAILURE(SetParameter());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+TEST_P(AudioEffectTest, SetAndGetParameter) {
+    OpenEffects();
+    VerifyParameters();
+    initParamCommon(1 /* session */, 1 /* ioHandle */, 44100 /* iSampleRate */,
+                    44100 /* oSampleRate */);
+    SetParameter();
+    VerifyParameters();
+    CloseEffects();
 }
 
 // Verify parameters pass in set can be successfully get.
-TEST_P(AudioEffect, SetAndGetParameterInProcessing) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, SetAndGetParameterInProcessing) {
+    OpenEffects();
+    VerifyParameters();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    initParamCommon(1 /* session */, 1 /* ioHandle */, AudioDeviceType::IN_DEFAULT /* deviceType */,
-                    44100 /* iSampleRate */, 44100 /* oSampleRate */);
-    EXPECT_NO_FATAL_FAILURE(SetParameter());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    initParamCommon(1 /* session */, 1 /* ioHandle */, 44100 /* iSampleRate */,
+                    44100 /* oSampleRate */);
+    SetParameter();
+    VerifyParameters();
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    CloseEffects();
 }
 
 // Parameters kept after reset.
-TEST_P(AudioEffect, ResetAndVerifyParameter) {
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+TEST_P(AudioEffectTest, ResetAndVerifyParameter) {
+    OpenEffects();
+    VerifyParameters();
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    initParamCommon(1 /* session */, 1 /* ioHandle */, AudioDeviceType::IN_DEFAULT /* deviceType */,
-                    44100 /* iSampleRate */, 44100 /* oSampleRate */);
-    EXPECT_NO_FATAL_FAILURE(SetParameter());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::RESET));
+    initParamCommon(1 /* session */, 1 /* ioHandle */, 44100 /* iSampleRate */,
+                    44100 /* oSampleRate */);
+    SetParameter();
+    VerifyParameters();
+    CommandEffects(CommandId::RESET);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    VerifyParameters();
+    CloseEffects();
 }
 
 // Multiple instances of same implementation running.
-TEST_P(AudioEffect, MultipleInstancesRunning) {
-    EXPECT_NO_FATAL_FAILURE(CreateEffects(3));
+TEST_P(AudioEffectTest, MultipleInstancesRunning) {
+    CreateEffects(3);
     ExpectState(State::INIT);
-    EXPECT_NO_FATAL_FAILURE(OpenEffects());
+    OpenEffects();
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::START));
+    CommandEffects(CommandId::START);
     ExpectState(State::PROCESSING);
-    initParamCommon(1 /* session */, 1 /* ioHandle */, AudioDeviceType::IN_DEFAULT /* deviceType */,
-                    44100 /* iSampleRate */, 44100 /* oSampleRate */);
-    EXPECT_NO_FATAL_FAILURE(SetParameter());
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CommandEffects(CommandId::STOP));
+    initParamCommon(1 /* session */, 1 /* ioHandle */, 44100 /* iSampleRate */,
+                    44100 /* oSampleRate */);
+    SetParameter();
+    VerifyParameters();
+    CommandEffects(CommandId::STOP);
     ExpectState(State::IDLE);
-    EXPECT_NO_FATAL_FAILURE(VerifyParameters());
-    EXPECT_NO_FATAL_FAILURE(CloseEffects());
+    VerifyParameters();
+    CloseEffects();
 }
 
-INSTANTIATE_TEST_SUITE_P(AudioEffectTest, AudioEffect,
+// Send data to effects and expect it to consume by check statusMQ.
+TEST_P(AudioEffectTest, ExpectEffectsToConsumeDataInMQ) {
+    OpenEffects();
+    PrepareInputData(mWriteMQSize);
+
+    CommandEffects(CommandId::START);
+    writeToFmq(mWriteMQSize);
+    readFromFmq(mWriteMQSize);
+
+    ExpectState(State::PROCESSING);
+    CommandEffects(CommandId::STOP);
+    // cleanup
+    CommandEffects(CommandId::STOP);
+    ExpectState(State::IDLE);
+    CloseEffects();
+}
+
+INSTANTIATE_TEST_SUITE_P(AudioEffectTestTest, AudioEffectTest,
                          testing::ValuesIn(android::getAidlHalInstanceNames(IFactory::descriptor)),
                          android::PrintInstanceNameToString);
-GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(AudioEffect);
+GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(AudioEffectTest);
 
 int main(int argc, char** argv) {
     ::testing::InitGoogleTest(&argc, argv);
     ABinderProcess_setThreadPoolMaxThreadCount(1);
     ABinderProcess_startThreadPool();
     return RUN_ALL_TESTS();
-}
\ No newline at end of file
+}
diff --git a/audio/aidl/vts/VtsHalEqualizerTargetTest.cpp b/audio/aidl/vts/VtsHalEqualizerTargetTest.cpp
new file mode 100644
index 0000000..3b9699b
--- /dev/null
+++ b/audio/aidl/vts/VtsHalEqualizerTargetTest.cpp
@@ -0,0 +1,233 @@
+/*
+ * Copyright (C) 2022 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.
+ */
+
+#include <algorithm>
+#include <limits>
+#include <map>
+#include <memory>
+#include <string>
+#include <vector>
+
+#define LOG_TAG "VtsHalEqualizerTest"
+
+#include <aidl/Gtest.h>
+#include <aidl/Vintf.h>
+#include <android-base/logging.h>
+#include <android-base/properties.h>
+#include <android/binder_interface_utils.h>
+#include <android/binder_manager.h>
+#include <android/binder_process.h>
+#include <gtest/gtest.h>
+
+#include <Utils.h>
+#include <aidl/android/hardware/audio/effect/IEffect.h>
+#include <aidl/android/hardware/audio/effect/IFactory.h>
+#include <aidl/android/media/audio/common/AudioChannelLayout.h>
+#include <aidl/android/media/audio/common/AudioDeviceType.h>
+
+#include "AudioHalBinderServiceUtil.h"
+#include "EffectHelper.h"
+#include "TestUtils.h"
+#include "effect-impl/EffectUUID.h"
+
+using namespace android;
+
+using aidl::android::hardware::audio::effect::Capability;
+using aidl::android::hardware::audio::effect::Descriptor;
+using aidl::android::hardware::audio::effect::EffectNullUuid;
+using aidl::android::hardware::audio::effect::Equalizer;
+using aidl::android::hardware::audio::effect::EqualizerTypeUUID;
+using aidl::android::hardware::audio::effect::IEffect;
+using aidl::android::hardware::audio::effect::IFactory;
+using aidl::android::hardware::audio::effect::Parameter;
+
+/**
+ * Here we focus on specific parameter checking, general IEffect interfaces testing performed in
+ * VtsAudioEfectTargetTest.
+ */
+using EqualizerParamTestParam = std::tuple<int, int, int>;
+
+class EqualizerParamTest : public ::testing::TestWithParam<EqualizerParamTestParam>,
+                           public EffectHelper {
+  public:
+    EqualizerParamTest()
+        : EffectHelper(android::getAidlHalInstanceNames(IFactory::descriptor)[0]),
+          mParamPresetIndex(std::get<0 /* kPresetIndexRange */>(GetParam())),
+          mParamBandIndex(std::get<1 /* kBandIndexRange */>(GetParam())),
+          mParamBandLevel(std::get<2 /* kBandLevelRange */>(GetParam())) {}
+
+    void SetUp() override {
+        CreateEffectsWithUUID(EqualizerTypeUUID);
+        initParamCommonFormat();
+        initParamCommon();
+        initParamSpecific();
+        OpenEffects(EqualizerTypeUUID);
+        SCOPED_TRACE(testing::Message() << "preset: " << mParamPresetIndex << " bandIdx "
+                                        << mParamBandIndex << " level " << mParamBandLevel);
+    }
+
+    void TearDown() override {
+        CloseEffects();
+        DestroyEffects();
+        CleanUp();
+    }
+
+    const int mParamPresetIndex;
+    const int mParamBandIndex;
+    const int mParamBandLevel;
+
+    void SetAndGetEqualizerParameters() {
+        auto functor = [&](const std::shared_ptr<IEffect>& effect) {
+            for (auto& it : mTags) {
+                auto& tag = it.first;
+                auto& eq = it.second;
+
+                // validate parameter
+                Descriptor desc;
+                ASSERT_STATUS(EX_NONE, effect->getDescriptor(&desc));
+                const bool valid = isTagInRange(it.first, it.second, desc);
+                const binder_exception_t expected = valid ? EX_NONE : EX_ILLEGAL_ARGUMENT;
+
+                // set
+                Parameter expectParam;
+                Parameter::Specific specific;
+                specific.set<Parameter::Specific::equalizer>(*eq.get());
+                expectParam.set<Parameter::specific>(specific);
+                EXPECT_STATUS(expected, effect->setParameter(expectParam))
+                        << expectParam.toString();
+
+                // get
+                if (expected == EX_NONE) {
+                    Parameter getParam;
+                    Parameter::Specific::Id id;
+                    id.set<Parameter::Specific::Id::equalizerTag>(tag);
+                    // if set success, then get should match
+                    EXPECT_STATUS(expected, effect->getParameter(id, &getParam));
+                    EXPECT_EQ(expectParam, getParam) << "\n"
+                                                     << expectParam.toString() << "\n"
+                                                     << getParam.toString();
+                }
+            }
+        };
+        EXPECT_NO_FATAL_FAILURE(ForEachEffect(functor));
+    }
+
+    void addPresetParam(int preset) {
+        Equalizer eq;
+        eq.set<Equalizer::preset>(preset);
+        mTags.push_back({Equalizer::preset, std::make_unique<Equalizer>(std::move(eq))});
+    }
+
+    void addBandLevelsParam(std::vector<Equalizer::BandLevel>& bandLevels) {
+        Equalizer eq;
+        eq.set<Equalizer::bandLevels>(bandLevels);
+        mTags.push_back({Equalizer::bandLevels, std::make_unique<Equalizer>(std::move(eq))});
+    }
+
+    bool isTagInRange(const Equalizer::Tag& tag, const std::unique_ptr<Equalizer>& eq,
+                      const Descriptor& desc) const {
+        std::cout << "xxx" << toString(tag) << " " << desc.toString();
+        const Equalizer::Capability& eqCap = desc.capability.get<Capability::equalizer>();
+        switch (tag) {
+            case Equalizer::preset: {
+                int index = eq->get<Equalizer::preset>();
+                return isPresetIndexInRange(eqCap, index);
+            }
+            case Equalizer::bandLevels: {
+                auto& bandLevel = eq->get<Equalizer::bandLevels>();
+                return isBandIndexInRange(eqCap, bandLevel);
+            }
+            default:
+                return false;
+        }
+        return false;
+    }
+
+    bool isPresetIndexInRange(const Equalizer::Capability& cap, int idx) const {
+        const auto [min, max] =
+                std::minmax_element(cap.presets.begin(), cap.presets.end(),
+                                    [](const auto& a, const auto& b) { return a.index < b.index; });
+        return idx >= min->index && idx <= max->index;
+    }
+
+    bool isBandIndexInRange(const Equalizer::Capability& cap,
+                            const std::vector<Equalizer::BandLevel>& bandLevel) const {
+        for (auto& it : bandLevel) {
+            if (!isBandIndexInRange(cap, it.index)) return false;
+        }
+        return true;
+    }
+
+    bool isBandIndexInRange(const Equalizer::Capability& cap, int idx) const {
+        const auto [min, max] =
+                std::minmax_element(cap.bandFrequencies.begin(), cap.bandFrequencies.end(),
+                                    [](const auto& a, const auto& b) { return a.index < b.index; });
+        return idx >= min->index && idx <= max->index;
+    }
+
+  private:
+    Equalizer::VendorExtension mVendorExtension;
+    std::vector<std::pair<Equalizer::Tag, std::unique_ptr<Equalizer>>> mTags;
+
+    bool validCapabilityTag(Capability& cap) { return cap.getTag() == Capability::equalizer; }
+
+    void initParamSpecific() {
+        Equalizer eq;
+        eq.set<Equalizer::preset>(0);
+        Parameter::Specific specific;
+        specific.set<Parameter::Specific::equalizer>(eq);
+        setSpecific(specific);
+    }
+
+    void CleanUp() { mTags.clear(); }
+};
+
+TEST_P(EqualizerParamTest, SetAndGetPreset) {
+    EXPECT_NO_FATAL_FAILURE(addPresetParam(mParamPresetIndex));
+    SetAndGetEqualizerParameters();
+}
+
+TEST_P(EqualizerParamTest, SetAndGetSingleBand) {
+    Equalizer::BandLevel bandLevel = {mParamBandIndex, mParamBandLevel};
+    std::vector<Equalizer::BandLevel> bandLevels;
+    bandLevels.push_back(bandLevel);
+    EXPECT_NO_FATAL_FAILURE(addBandLevelsParam(bandLevels));
+    SetAndGetEqualizerParameters();
+}
+
+/**
+ Testing preset index range with [-10, 10], assuming the min/max preset index supported by
+effect is in this range.
+ This range is verified with IEffect.getDescriptor(): for any index supported vts expect EX_NONE
+from IEffect.setParameter(), otherwise expect EX_ILLEGAL_ARGUMENT.
+ */
+constexpr std::pair<int, int> kPresetIndexRange = {-1, 10};  // valid range [0, 9]
+constexpr std::pair<int, int> kBandIndexRange = {-1, 5};     // valid range [0, 4]
+constexpr std::pair<int, int> kBandLevelRange = {-5, 5};     // needs update with implementation
+
+INSTANTIATE_TEST_SUITE_P(
+        EqualizerTest, EqualizerParamTest,
+        ::testing::Combine(testing::Range(kPresetIndexRange.first, kPresetIndexRange.second),
+                           testing::Range(kBandIndexRange.first, kBandIndexRange.second),
+                           testing::Range(kBandLevelRange.first, kBandLevelRange.second)));
+GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(EqualizerTest);
+
+int main(int argc, char** argv) {
+    ::testing::InitGoogleTest(&argc, argv);
+    ABinderProcess_setThreadPoolMaxThreadCount(1);
+    ABinderProcess_startThreadPool();
+    return RUN_ALL_TESTS();
+}
