diff options
Diffstat (limited to 'media')
-rw-r--r-- | media/eco/ECOData.cpp | 138 | ||||
-rw-r--r-- | media/eco/include/eco/ECOData.h | 102 | ||||
-rw-r--r-- | media/eco/include/eco/ECODataKey.h | 6 | ||||
-rw-r--r-- | media/eco/tests/Android.bp | 19 | ||||
-rw-r--r-- | media/eco/tests/EcoDataTest.cpp | 303 | ||||
-rw-r--r-- | media/eco/tests/run_all_unit_tests.sh | 10 |
6 files changed, 573 insertions, 5 deletions
diff --git a/media/eco/ECOData.cpp b/media/eco/ECOData.cpp index bb3fe1a..0f32e53 100644 --- a/media/eco/ECOData.cpp +++ b/media/eco/ECOData.cpp @@ -19,10 +19,12 @@ #include <utils/Errors.h> #include <utils/Log.h> +#include <string> #include <binder/Parcel.h> #include "eco/ECOData.h" +#include "eco/ECODataKey.h" namespace android { namespace media { @@ -33,15 +35,151 @@ using namespace ::android; status_t ECOData::readFromParcel(const Parcel* parcel) { parcel->readInt32(&mDataType); parcel->readInt64(&mDataTimeUs); + // TODO(hkuang): Add the implenmentation of reading all keys. return NO_ERROR; } status_t ECOData::writeToParcel(Parcel* parcel) const { parcel->writeInt32(mDataType); parcel->writeInt64(mDataTimeUs); + // TODO(hkuang): Add the implenmentation of writing all keys. return NO_ERROR; } +void ECOData::init() { + mKeyValueStore[ECO_DATA_KEY_TYPE] = mDataType; + mKeyValueStore[ECO_DATA_KEY_TIME_US] = mDataTimeUs; +} + +int32_t ECOData::getDataType() { + return mDataType; +} + +int64_t ECOData::getDataTimeUs() { + return mDataTimeUs; +} + +// Inserts a new key into store if the key does not exist yet. Otherwise, this will override the +// existing key's value. +ECODataStatus ECOData::setString(const std::string& key, const std::string& value) { + if (key.empty() || value.empty()) { + return ECODataStatus::INVALID_ARGUMENT; + } + + mKeyValueStore[key] = value; + + // TODO(hkuang): Check the valueType is valid for the key. + return ECODataStatus::OK; +} + +ECODataStatus ECOData::findString(const std::string& key, std::string* value) const { + if (key.empty()) { + return ECODataStatus::INVALID_ARGUMENT; + } + + // Check if the key exists. + if (mKeyValueStore.find(key) == mKeyValueStore.end()) { + return ECODataStatus::KEY_NOT_EXIST; + } + + // Safely access the value. + const std::string& entryValue = std::get<std::string>(mKeyValueStore.at(key)); + value->assign(entryValue); + + return ECODataStatus::OK; +} + +// Inserts a new key into store if the key does not exist yet. Otherwise, this will override the +// existing key's value. +template <typename T> +ECODataStatus ECOData::setValue(const std::string& key, T value) { + if (key.empty()) { + return ECODataStatus::INVALID_ARGUMENT; + } + + mKeyValueStore[key] = value; + return ECODataStatus::OK; +} + +template <typename T> +ECODataStatus ECOData::findValue(const std::string& key, T* out) const { + if (key.empty() || out == nullptr) { + return ECODataStatus::INVALID_ARGUMENT; + } + + if (mKeyValueStore.find(key) == mKeyValueStore.end()) { + return ECODataStatus::KEY_NOT_EXIST; + } + + // Safely access the value. + *out = std::get<T>(mKeyValueStore.at(key)); + + return ECODataStatus::OK; +} + +ECODataStatus ECOData::setInt32(const std::string& key, int32_t value) { + return setValue<int32_t>(key, value); +} + +ECODataStatus ECOData::findInt32(const std::string& key, int32_t* out) const { + return findValue<int32_t>(key, out); +} + +ECODataStatus ECOData::setInt64(const std::string& key, int64_t value) { + return setValue<int64_t>(key, value); +} + +ECODataStatus ECOData::findInt64(const std::string& key, int64_t* out) const { + return findValue<int64_t>(key, out); +} + +ECODataStatus ECOData::setDouble(const std::string& key, double value) { + return setValue<double>(key, value); +} + +ECODataStatus ECOData::findDouble(const std::string& key, double* out) const { + return findValue<double>(key, out); +} + +ECODataStatus ECOData::setSize(const std::string& key, size_t value) { + return setValue<size_t>(key, value); +} + +ECODataStatus ECOData::findSize(const std::string& key, size_t* out) const { + return findValue<size_t>(key, out); +} + +ECODataStatus ECOData::setFloat(const std::string& key, float value) { + return setValue<float>(key, value); +} + +ECODataStatus ECOData::findFloat(const std::string& key, float* out) const { + return findValue<float>(key, out); +} + +ECODataStatus ECOData::set(const std::string& key, const ECOData::ECODataValueType& value) { + if (key.empty()) { + return ECODataStatus::INVALID_ARGUMENT; + } + mKeyValueStore[key] = value; + return ECODataStatus::OK; +} + +ECODataStatus ECOData::find(const std::string& key, ECOData::ECODataValueType* out) const { + if (key.empty() || out == nullptr) { + return ECODataStatus::INVALID_ARGUMENT; + } + + if (mKeyValueStore.find(key) == mKeyValueStore.end()) { + return ECODataStatus::KEY_NOT_EXIST; + } + + // Safely access the value. + *out = mKeyValueStore.at(key); + + return ECODataStatus::OK; +} + } // namespace eco } // namespace media } // namespace android
\ No newline at end of file diff --git a/media/eco/include/eco/ECOData.h b/media/eco/include/eco/ECOData.h index 9c17320..37b048c 100644 --- a/media/eco/include/eco/ECOData.h +++ b/media/eco/include/eco/ECOData.h @@ -19,11 +19,23 @@ #include <binder/Parcel.h> #include <binder/Parcelable.h> +#include <string> +#include <unordered_map> +#include <variant> namespace android { namespace media { namespace eco { +enum class ECODataStatus { + OK, + FAIL_TO_INSERT, + INVALID_ECODATA_TYPE, + KEY_NOT_EXIST, + INVALID_VALUE_TYPE, + INVALID_ARGUMENT, +}; + /** * ECOData is the container for all messages passed between different components in ECOService. * All messages in ECOServices are represented by a list of key-value pairs. @@ -31,14 +43,40 @@ namespace eco { * "bit-rate" -> 22000000 * "Provider-Name" -> "QCOM-Video-Encoder". * "avg-frame-qp" -> 40 -* ECOData follows the same design pattern of AMessage and Metadata in Media Framework. -* TODO(hkuang): Add the implementation and sample usage. +* ECOData follows the same design pattern of AMessage and Metadata in Media Framework. The key +* must be non-empty string. Below are the supported data types: +* +* // Item types set/find function suffixes +* // ========================================== +* // int32_t Int32 +* // int64_t Int64 +* // size_t Size +* // float Float +* // double Double +* // String String +* +* ECOData does not support duplicate keys with different values. When inserting a key-value pair, +* a new entry will be created if the key does not exist. Othewise, they key's value will be +* overwritten with the new value. +* +* Sample usage: +* +* // Create the ECOData +* std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); +* +* // Set the encoder name. +* data->setString("stats-encoder-type", "google-avc"); +* +* // Set encoding bitrate. +* data->setInt32("stats-encoder-target-bitrate-bps", 22000000); */ class ECOData : public Parcelable { public: - ECOData() : mDataType(0), mDataTimeUs(-1) {} - ECOData(int32_t type) : mDataType(type), mDataTimeUs(-1) {} - ECOData(int32_t type, int64_t timeUs) : mDataType(type), mDataTimeUs(timeUs) {} + using ECODataValueType = std::variant<int32_t, int64_t, size_t, float, double, std::string>; + + ECOData() : mDataType(0), mDataTimeUs(-1) { init(); } + ECOData(int32_t type) : mDataType(type), mDataTimeUs(-1) { init(); } + ECOData(int32_t type, int64_t timeUs) : mDataType(type), mDataTimeUs(timeUs) { init(); } // Constants for mDataType. enum { @@ -53,13 +91,58 @@ public: DATA_TYPE_INFO_LISTENER_OPTON = 4, }; + // set/find functions that could be used for all the value types. + ECODataStatus set(const std::string& key, const ECODataValueType& value); + ECODataStatus find(const std::string& key, ECODataValueType* out) const; + + // Convenient set/find functions for string value type. + ECODataStatus setString(const std::string& key, const std::string& value); + ECODataStatus findString(const std::string& key, std::string* out) const; + + // Convenient set/find functions for int32_t value type. + ECODataStatus setInt32(const std::string& key, int32_t value); + ECODataStatus findInt32(const std::string& key, int32_t* out) const; + + // Convenient set/find functions for int64_t value type. + ECODataStatus setInt64(const std::string& key, int64_t value); + ECODataStatus findInt64(const std::string& key, int64_t* out) const; + + // Convenient set/find functions for float value type. + ECODataStatus setFloat(const std::string& key, float value); + ECODataStatus findFloat(const std::string& key, float* out) const; + + // Convenient set/find functions for double value type. + ECODataStatus setDouble(const std::string& key, double value); + ECODataStatus findDouble(const std::string& key, double* out) const; + + // Convenient set/find functions for size_t value type. + ECODataStatus setSize(const std::string& key, size_t value); + ECODataStatus findSize(const std::string& key, size_t* out) const; + /** * Serialization over Binder */ status_t readFromParcel(const Parcel* parcel) override; status_t writeToParcel(Parcel* parcel) const override; + /* Returns the type of the data. */ + int32_t getDataType(); + + /* Returns the timestamp associated with the data. */ + int64_t getDataTimeUs(); + + /* Sets the type of the data. */ + void setDataType(int32_t type); + + /* Sets the timestamp associated with the data. */ + void setDataTimeUs(); + + /* Gets the number of keys in the ECOData. */ + size_t getNumOfEntries() { return mKeyValueStore.size(); } + private: + void init(); + /* The type of the data */ int32_t mDataType; @@ -67,6 +150,15 @@ private: // boottime time base. This is only used when the data type is stats or info. -1 means // unavailable. int64_t mDataTimeUs; + + // Internal store for the key value pairs. + std::unordered_map<std::string, ECODataValueType> mKeyValueStore; + + template <typename T> + ECODataStatus setValue(const std::string& key, T value); + + template <typename T> + ECODataStatus findValue(const std::string& key, T* out) const; }; } // namespace eco diff --git a/media/eco/include/eco/ECODataKey.h b/media/eco/include/eco/ECODataKey.h index 7945ea0..0856e01 100644 --- a/media/eco/include/eco/ECODataKey.h +++ b/media/eco/include/eco/ECODataKey.h @@ -86,6 +86,12 @@ constexpr char INFO_KEY_FRAME_TYPE[] = "info-frame-type"; constexpr char INFO_KEY_FRAME_SIZE_BYTES[] = "info-frame-size-bytes"; constexpr char INFO_KEY_CURRENT_BITRATE_BPS[] = "info-current-bitrate-bps"; +// ================================================================================================ +// Standard ECOData keys. +// ================================================================================================ +constexpr char ECO_DATA_KEY_TYPE[] = "eco-data-type"; +constexpr char ECO_DATA_KEY_TIME_US[] = "eco-data-time-us"; + } // namespace eco } // namespace media } // namespace android diff --git a/media/eco/tests/Android.bp b/media/eco/tests/Android.bp new file mode 100644 index 0000000..543885c --- /dev/null +++ b/media/eco/tests/Android.bp @@ -0,0 +1,19 @@ +cc_defaults{ + name : "libmedia_ecoservice_tests_defaults", + cflags : [ + "-Wall", + "-Werror", + ], +} + +cc_test { + name: "EcoDataTest", + defaults: ["libmedia_ecoservice_tests_defaults"], + srcs: ["EcoDataTest.cpp"], + shared_libs: [ + "libbinder", + "libcutils", + "libutils", + "libmedia_ecoservice", + ], +} diff --git a/media/eco/tests/EcoDataTest.cpp b/media/eco/tests/EcoDataTest.cpp new file mode 100644 index 0000000..fb9e2a1 --- /dev/null +++ b/media/eco/tests/EcoDataTest.cpp @@ -0,0 +1,303 @@ +/* + * Copyright (C) 2019 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. + */ + +// Unit Test for EcoData. + +#include <math.h> +#include <stdlib.h> + +#include <android-base/unique_fd.h> +#include <binder/Parcel.h> +#include <binder/Parcelable.h> +#include <cutils/ashmem.h> +#include <gtest/gtest.h> +#include <sys/mman.h> + +#include "eco/ECOData.h" +#include "eco/ECODataKey.h" + +namespace android { +namespace media { +namespace eco { + +TEST(EcoDataTest, TestConstructor1) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(); + EXPECT_EQ(data->getDataType(), ECOData::DATA_TYPE_UNKNOWN); + EXPECT_EQ(data->getDataTimeUs(), -1); + + int32_t type; + EXPECT_TRUE(data->findInt32(ECO_DATA_KEY_TYPE, &type) == ECODataStatus::OK); + EXPECT_EQ(type, ECOData::DATA_TYPE_UNKNOWN); + + int64_t time; + EXPECT_TRUE(data->findInt64(ECO_DATA_KEY_TIME_US, &time) == ECODataStatus::OK); + EXPECT_EQ(time, -1); +} + +TEST(EcoDataTest, TestConstructor2) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS); + EXPECT_EQ(data->getDataType(), ECOData::DATA_TYPE_STATS); + EXPECT_EQ(data->getDataTimeUs(), -1); +} + +TEST(EcoDataTest, TestConstructor3) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + EXPECT_EQ(data->getDataType(), ECOData::DATA_TYPE_STATS); + EXPECT_EQ(data->getDataTimeUs(), 1000); +} + +TEST(EcoDataTest, TestNormalSetAndFindString) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + data->setString(STATS_KEY_ENCODER_TYPE, "avc"); + std::string testValue; + EXPECT_TRUE(data->findString(STATS_KEY_ENCODER_TYPE, &testValue) == ECODataStatus::OK); + EXPECT_EQ(testValue, "avc"); + + // Override existing key. + data->setString(STATS_KEY_ENCODER_TYPE, "hevc"); + EXPECT_EQ(data->findString(STATS_KEY_ENCODER_TYPE, &testValue), ECODataStatus::OK); + EXPECT_EQ(testValue, "hevc"); +} + +TEST(EcoDataTest, TestSetAndFindMultipleString) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + std::unordered_map<std::string, std::string> inputEntries = { + {"name1", "avc"}, {"name2", "avc2"}, {"name3", "avc3"}, {"name4", "avc4"}, + {"name5", "avc5"}, {"name6", "avc6"}, {"name7", "avc7"}, {"name8", "avc8"}, + {"name9", "avc9"}, {"name10", "avc10"}, {"name11", "avc11"}, {"name12", "avc12"}}; + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + data->setString(it->first, it->second); + } + + // Checks if the string exist in the ECOData. + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + std::string testValue; + EXPECT_TRUE(data->findString(it->first, &testValue) == ECODataStatus::OK); + EXPECT_EQ(testValue, it->second); + } +} + +TEST(EcoDataTest, TestSetAndFindInvalidString) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + // Test read to null ptr and expect failure + EXPECT_TRUE(data->findString("encoder-name", nullptr) != ECODataStatus::OK); + + // Test find non-existing key and expect failure. + std::string testValue; + EXPECT_TRUE(data->findString("encoder-name", &testValue) != ECODataStatus::OK); + + // Test set empty key and expect failure + EXPECT_TRUE(data->setString("", "avc") != ECODataStatus::OK); + + // Test read empty key and expect failure + EXPECT_TRUE(data->findString("", &testValue) != ECODataStatus::OK); +} + +TEST(EcoDataTest, TestNormalSetAndFindInt32) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + data->setInt32(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, 2000000); + int32_t testValue; + EXPECT_TRUE(data->findInt32(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, &testValue) == + ECODataStatus::OK); + EXPECT_EQ(testValue, 2000000); + + // Override existing key. + data->setInt32(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, 2200000); + EXPECT_EQ(data->findInt32(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, &testValue), ECODataStatus::OK); + EXPECT_EQ(testValue, 2200000); +} + +TEST(EcoDataTest, TestSetAndFindMultipleInt32) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + std::unordered_map<std::string, int32_t> inputEntries = { + {"name1", 100}, {"name2", 200}, {"name3", 300}, {"name4", 400}, + {"name5", 500}, {"name6", 600}, {"name7", 700}, {"name8", 800}, + {"name9", 900}, {"name10", 10000}, {"name11", 110000}, {"name12", 120000}}; + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + data->setInt32(it->first, it->second); + } + + // Checks if the string exist in the ECOData. + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + int32_t testValue; + EXPECT_TRUE(data->findInt32(it->first, &testValue) == ECODataStatus::OK); + EXPECT_EQ(testValue, it->second); + } +} + +TEST(EcoDataTest, TestSetAndFindInvalidInt32) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + // Test read to null ptr and expect failure + EXPECT_TRUE(data->findInt32("encoder-name", nullptr) != ECODataStatus::OK); + + // Test find non-existing key and expect failure. + int32_t testValue; + EXPECT_TRUE(data->findInt32("encoder-name", &testValue) != ECODataStatus::OK); + + // Test set empty key and expect failure + EXPECT_TRUE(data->setInt32("", 1000) != ECODataStatus::OK); + + // Test read empty key and expect failure + EXPECT_TRUE(data->findInt32("", &testValue) != ECODataStatus::OK); +} + +TEST(EcoDataTest, TestNormalSetAndFindInt64) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + data->setInt64(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, 2000000); + int64_t testValue; + EXPECT_TRUE(data->findInt64(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, &testValue) == + ECODataStatus::OK); + EXPECT_EQ(testValue, 2000000); + + // Override existing key. + data->setInt64(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, 2200000); + EXPECT_EQ(data->findInt64(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, &testValue), ECODataStatus::OK); + EXPECT_EQ(testValue, 2200000); +} + +TEST(EcoDataTest, TestNormalSetAndFindMultipleInt64) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + std::unordered_map<std::string, int64_t> inputEntries = { + {"name1", 100}, {"name2", 200}, {"name3", 300}, {"name4", 400}, + {"name5", 500}, {"name6", 600}, {"name7", 700}, {"name8", 800}, + {"name9", 900}, {"name10", 10000}, {"name11", 110000}, {"name12", 120000}}; + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + data->setInt64(it->first, it->second); + } + + // Checks if the string exist in the ECOData. + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + int64_t testValue; + EXPECT_TRUE(data->findInt64(it->first, &testValue) == ECODataStatus::OK); + EXPECT_EQ(testValue, it->second); + } +} + +TEST(EcoDataTest, TestSetAndFindInvalidInt64) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + // Test read to null ptr and expect failure + EXPECT_TRUE(data->findInt64("encoder-name", nullptr) != ECODataStatus::OK); + + // Test find non-existing key and expect failure. + int64_t testValue; + EXPECT_TRUE(data->findInt64("encoder-name", &testValue) != ECODataStatus::OK); + + // Test set empty key and expect failure + EXPECT_TRUE(data->setInt64("", 1000) != ECODataStatus::OK); + + // Test read empty key and expect failure + EXPECT_TRUE(data->findInt64("", &testValue) != ECODataStatus::OK); +} + +TEST(EcoDataTest, TestNormalSetAndFindFloat) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + data->setFloat(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, 2000000.0); + float testValue; + EXPECT_TRUE(data->findFloat(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, &testValue) == + ECODataStatus::OK); + EXPECT_FLOAT_EQ(testValue, 2000000.0); + + // Override existing key. + data->setFloat(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, 2200000.0); + EXPECT_TRUE(data->findFloat(STATS_KEY_ENCODER_TARGET_BITRATE_BPS, &testValue) == + ECODataStatus::OK); + EXPECT_FLOAT_EQ(testValue, 2200000.0); +} + +TEST(EcoDataTest, TestNormalSetAndFindMultipleFloat) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + std::unordered_map<std::string, float> inputEntries = { + {"name1", 100.0}, {"name2", 200.0}, {"name3", 300.0}, {"name4", 400.0}, + {"name5", 500.0}, {"name6", 600.0}, {"name7", 700.0}, {"name8", 800.0}, + {"name9", 900.0}, {"name10", 10000.0}, {"name11", 110000.0}, {"name12", 120000.0}}; + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + data->setFloat(it->first, it->second); + } + + // Checks if the string exist in the ECOData. + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + float testValue; + EXPECT_TRUE(data->findFloat(it->first, &testValue) == ECODataStatus::OK); + EXPECT_FLOAT_EQ(testValue, it->second); + } +} + +TEST(EcoDataTest, TestSetAndFindInvalidFloat) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + // Test read to null ptr and expect failure + EXPECT_TRUE(data->findFloat("encoder-name", nullptr) != ECODataStatus::OK); + + // Test find non-existing key and expect failure. + float testValue; + EXPECT_TRUE(data->findFloat("encoder-name", &testValue) != ECODataStatus::OK); + + // Test set empty key and expect failure + EXPECT_TRUE(data->setFloat("", 1000.0) != ECODataStatus::OK); + + // Test read empty key and expect failure + EXPECT_TRUE(data->findFloat("", &testValue) != ECODataStatus::OK); +} + +TEST(EcoDataTest, TestNormalSetAndFindMixedDataType) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + std::unordered_map<std::string, ECOData::ECODataValueType> inputEntries = { + {"name1", "google-encoder"}, {"name2", "avc"}, {"profile", 1}, {"level", 2}, + {"framerate", 4.1}, {"kfi", 30}}; + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + data->set(it->first, it->second); + } + + // Checks if the string exist in the ECOData. + for (auto it = inputEntries.begin(); it != inputEntries.end(); ++it) { + ECOData::ECODataValueType testValue; + EXPECT_TRUE(data->find(it->first, &testValue) == ECODataStatus::OK); + EXPECT_EQ(testValue, it->second); + } +} + +TEST(EcoDataTest, TestSetAndFindInvalidDataType) { + std::unique_ptr<ECOData> data = std::make_unique<ECOData>(ECOData::DATA_TYPE_STATS, 1000); + + // Test read to null ptr and expect failure + EXPECT_TRUE(data->find("encoder-name", nullptr) != ECODataStatus::OK); + + // Test find non-existing key and expect failure. + ECOData::ECODataValueType testValue; + EXPECT_TRUE(data->find("encoder-name2", &testValue) != ECODataStatus::OK); + + // Test set empty key and expect failure + EXPECT_TRUE(data->set("", 1000) != ECODataStatus::OK); + + // Test read empty key and expect failure + EXPECT_TRUE(data->find("", &testValue) != ECODataStatus::OK); +} + +} // namespace eco +} // namespace media +} // namespace android
\ No newline at end of file diff --git a/media/eco/tests/run_all_unit_tests.sh b/media/eco/tests/run_all_unit_tests.sh new file mode 100644 index 0000000..0b5fee0 --- /dev/null +++ b/media/eco/tests/run_all_unit_tests.sh @@ -0,0 +1,10 @@ +#!/bin/bash +if [ -z "$ANDROID_BUILD_TOP" ]; then + echo "Android build environment not set" + exit -1 +fi + +echo "waiting for device" +adb root && adb wait-for-device remount && adb sync + +adb shell /data/nativetest/EcoDataTest/EcoDataTest |