1/*
2 * Copyright (C) 2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#include "gtest/gtest.h"
17
18#include "native_common_utils.h"
19#include "effect_json_helper.h"
20#include "common_utils.h"
21#include "string_helper.h"
22#include "format_helper.h"
23#include "native_effect_base.h"
24#include "memcpy_helper.h"
25
26using namespace testing::ext;
27namespace {
28    const float YUV_BYTES_PER_PIXEL = 1.5f;
29    const int32_t P10_BYTES_PER_LUMA = 2;
30    const u_int32_t RGBA_BYTES_PER_PIXEL = 4;
31    constexpr uint32_t WIDTH = 1920;
32    constexpr uint32_t HEIGHT = 1080;
33    constexpr uint32_t MAX_ALLOC_SIZE = 600 * 1024 * 1024;
34}
35
36namespace OHOS {
37namespace Media {
38namespace Effect {
39namespace Test {
40
41class TestUtils : public testing::Test {
42public:
43    TestUtils() = default;
44
45    ~TestUtils() override = default;
46    static void SetUpTestCase() {}
47
48    static void TearDownTestCase() {}
49
50    void SetUp() override{}
51
52    void TearDown() override{}
53};
54
55HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny001, TestSize.Level1) {
56    ImageEffect_Any value;
57    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_INT32;
58    value.dataValue.int32Value = 123;
59    Plugin::Any any;
60    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
61    ASSERT_EQ(result, ErrorCode::SUCCESS);
62    int actualValue = Plugin::AnyCast<int>(any);
63    ASSERT_EQ(actualValue, 123);
64}
65
66HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny002, TestSize.Level1) {
67    ImageEffect_Any value;
68    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_FLOAT;
69    value.dataValue.floatValue = 123.45f;
70    Plugin::Any any;
71    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
72    ASSERT_EQ(result, ErrorCode::SUCCESS);
73    float actualValue = Plugin::AnyCast<float>(any);
74    ASSERT_EQ(actualValue, 123.45f);
75}
76
77HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny003, TestSize.Level1) {
78    ImageEffect_Any value;
79    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_DOUBLE;
80    value.dataValue.doubleValue = 123.45;
81    Plugin::Any any;
82    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
83    ASSERT_EQ(result, ErrorCode::SUCCESS);
84    double actualValue = Plugin::AnyCast<double>(any);
85    ASSERT_EQ(actualValue, 123.45);
86}
87
88HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny004, TestSize.Level1) {
89    ImageEffect_Any value;
90    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_CHAR;
91    value.dataValue.charValue = 'A';
92    Plugin::Any any;
93    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
94    ASSERT_EQ(result, ErrorCode::SUCCESS);
95    ASSERT_EQ(Plugin::AnyCast<char>(any), 'A');
96}
97
98HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny005, TestSize.Level1) {
99    ImageEffect_Any value;
100    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_LONG;
101    value.dataValue.longValue = 123456789L;
102    Plugin::Any any;
103    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
104    ASSERT_EQ(result, ErrorCode::SUCCESS);
105    ASSERT_EQ(Plugin::AnyCast<long>(any), 123456789L);
106}
107
108HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny006, TestSize.Level1) {
109    ImageEffect_Any value;
110    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_PTR;
111    value.dataValue.ptrValue = (void*)0x12345678;
112    Plugin::Any any;
113    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
114    ASSERT_EQ(result, ErrorCode::SUCCESS);
115    ASSERT_EQ(Plugin::AnyCast<void*>(any), reinterpret_cast<void*>(0x12345678));
116}
117
118HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny007, TestSize.Level1) {
119    ImageEffect_Any value;
120    Plugin::Any any;
121    ErrorCode result = NativeCommonUtils::ParseOHAny(&value, any);
122    ASSERT_NE(result, ErrorCode::SUCCESS);
123}
124
125HWTEST_F(TestUtils, NativeCommonUtilsParseOHAny008, TestSize.Level1) {
126    ImageEffect_Any value;
127    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_BOOL;
128    value.dataValue.boolValue = true;
129    Plugin::Any any;
130    EXPECT_EQ(NativeCommonUtils::ParseOHAny(&value, any), ErrorCode::SUCCESS);
131}
132
133HWTEST_F(TestUtils, NativeCommonUtilsSwitchToOHAny001, TestSize.Level1) {
134    Plugin::Any any = 10.0;
135    ImageEffect_Any value;
136    value.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_DOUBLE;
137    ErrorCode result = NativeCommonUtils::SwitchToOHAny(any, &value);
138    EXPECT_EQ(result, ErrorCode::SUCCESS);
139    EXPECT_DOUBLE_EQ(value.dataValue.doubleValue, 10.0);
140
141    Plugin::Any anyChar = 'a';
142    ImageEffect_Any valueChar;
143    valueChar.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_CHAR;
144    result = NativeCommonUtils::SwitchToOHAny(anyChar, &valueChar);
145    EXPECT_EQ(result, ErrorCode::SUCCESS);
146    EXPECT_EQ(valueChar.dataValue.charValue, 'a');
147
148    Plugin::Any anyLong = 10L;
149    ImageEffect_Any valueLong;
150    valueLong.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_LONG;
151    result = NativeCommonUtils::SwitchToOHAny(anyLong, &valueLong);
152    EXPECT_EQ(result, ErrorCode::SUCCESS);
153    EXPECT_EQ(valueLong.dataValue.longValue, 10L);
154
155    Plugin::Any anyPtr = (void*)10;
156    ImageEffect_Any valuePtr;
157    valuePtr.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_PTR;
158    result = NativeCommonUtils::SwitchToOHAny(anyPtr, &valuePtr);
159    EXPECT_EQ(result, ErrorCode::SUCCESS);
160    EXPECT_EQ(valuePtr.dataValue.ptrValue, (void*)10);
161
162    Plugin::Any anyBool = true;
163    ImageEffect_Any valueBool;
164    valueBool.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_BOOL;
165    result = NativeCommonUtils::SwitchToOHAny(anyBool, &valueBool);
166    EXPECT_EQ(result, ErrorCode::SUCCESS);
167    EXPECT_EQ(valueBool.dataValue.boolValue, true);
168
169    Plugin::Any anyUnknown = std::string("Unsupported");
170    ImageEffect_Any valueUnknown;
171    valueUnknown.dataType = ImageEffect_DataType::EFFECT_DATA_TYPE_UNKNOWN;
172    result = NativeCommonUtils::SwitchToOHAny(anyUnknown, &valueUnknown);
173    EXPECT_EQ(result, ErrorCode::ERR_NOT_SUPPORT_SWITCH_TO_OHANY);
174}
175
176HWTEST_F(TestUtils, JsonHelper001, TestSize.Level1) {
177    EffectJsonPtr root = EFFECTJsonHelper::CreateObject();
178    ASSERT_NE(root, nullptr);
179    ASSERT_TRUE(root->IsObject());
180    ASSERT_TRUE(root->Put("stringKey", "testString"));
181    ASSERT_TRUE(root->Put("floatKey", 1.23f));
182    ASSERT_TRUE(root->Put("intKey", 123));
183    EffectJsonPtr intRoot = EFFECTJsonHelper::CreateArray();
184    ASSERT_TRUE(intRoot->Add(1));
185    ASSERT_TRUE(intRoot->Add(2));
186    ASSERT_TRUE(intRoot->Add(3));
187    ASSERT_TRUE(root->Put("arrayKey", intRoot));
188
189    ASSERT_TRUE(root->HasElement("stringKey"));
190    EffectJsonPtr stringKeyJsonPtr = root->GetElement("stringKey");
191    ASSERT_NE(stringKeyJsonPtr, nullptr);
192    ASSERT_TRUE(stringKeyJsonPtr->IsString());
193    ASSERT_FALSE(stringKeyJsonPtr->IsNumber());
194    ASSERT_EQ(stringKeyJsonPtr->GetInt(), 0);
195    ASSERT_EQ(stringKeyJsonPtr->GetUInt(), 0);
196    ASSERT_EQ(stringKeyJsonPtr->GetFloat(), 0);
197    ASSERT_EQ(stringKeyJsonPtr->GetDouble(), 0);
198    ASSERT_FALSE(stringKeyJsonPtr->GetBool());
199    std::string stringValue = stringKeyJsonPtr->GetString();
200    ASSERT_STREQ(stringValue.c_str(), "testString");
201
202    ASSERT_TRUE(root->HasElement("floatKey"));
203    EffectJsonPtr floatKeyJsonPtr = root->GetElement("floatKey");
204    ASSERT_NE(floatKeyJsonPtr, nullptr);
205    ASSERT_TRUE(floatKeyJsonPtr->IsNumber());
206    ASSERT_TRUE(floatKeyJsonPtr->GetString().empty());
207    ASSERT_FALSE(floatKeyJsonPtr->IsString());
208    float floatValue = floatKeyJsonPtr->GetFloat();
209    ASSERT_EQ(floatValue, 1.23f);
210
211    ASSERT_FALSE(root->HasElement("nonExistKey"));
212
213    ASSERT_TRUE(root->HasElement("arrayKey"));
214    EffectJsonPtr arrayKeyJsonPtr = root->GetElement("arrayKey");
215    ASSERT_NE(arrayKeyJsonPtr, nullptr);
216    ASSERT_TRUE(arrayKeyJsonPtr->IsArray());
217    std::vector<EffectJsonPtr> arrayJsonPtr = arrayKeyJsonPtr->GetArray();
218    ASSERT_EQ(arrayJsonPtr.size(), 3);
219    ASSERT_EQ(arrayJsonPtr[0]->GetInt(), 1);
220    ASSERT_EQ(arrayJsonPtr[1]->GetInt(), 2);
221    ASSERT_EQ(arrayJsonPtr[2]->GetInt(), 3);
222}
223
224HWTEST_F(TestUtils, NativeCommonUtilsParseJson001, TestSize.Level1) {
225    std::string key = "test_key";
226    Plugin::Any any = nullptr;
227    Json *json = nullptr;
228    EffectJsonPtr result = std::make_shared<EffectJson>(json);
229    ErrorCode ret = CommonUtils::ParseAnyAndAddToJson(key, any, result);
230    ASSERT_EQ(ret, ErrorCode::ERR_ANY_CAST_TYPE_NOT_MATCH);
231}
232HWTEST_F(TestUtils, NativeCommonUtilsParseNativeWindowData001, TestSize.Level1) {
233    std::shared_ptr<BufferInfo> bufferinfo = std::make_unique<BufferInfo>();
234    void *addr = nullptr;
235    std::shared_ptr<ExtraInfo> extrainfo = std::make_unique<ExtraInfo>();
236    std::shared_ptr<EffectBuffer> effectBuffer = std::make_unique<EffectBuffer>(bufferinfo, addr, extrainfo);
237    DataType datatype = DataType::UNKNOWN;
238    ErrorCode result = CommonUtils::ParseNativeWindowData(effectBuffer, datatype);
239    ASSERT_EQ(result, ErrorCode::SUCCESS);
240}
241HWTEST_F(TestUtils, NativeCommonUtilsModifyPixelMapProperty001, TestSize.Level1) {
242    PixelMap pixelMap;
243    std::shared_ptr<BufferInfo> bufferinfo = std::make_unique<BufferInfo>();
244    void *addr = nullptr;
245    std::shared_ptr<ExtraInfo> extrainfo = std::make_unique<ExtraInfo>();
246    std::shared_ptr<EffectBuffer> buffer = std::make_unique<EffectBuffer>(bufferinfo, addr, extrainfo);
247    std::shared_ptr<EffectMemoryManager> memoryManager = std::make_unique<EffectMemoryManager>();
248    ErrorCode result = CommonUtils::ModifyPixelMapProperty(&pixelMap, buffer, memoryManager);
249    EXPECT_EQ(result, ErrorCode::ERR_ALLOC_MEMORY_FAIL);
250}
251HWTEST_F(TestUtils, StringHelper001, TestSize.Level1) {
252    std::string input = "abc";
253    std::string suffix = "abcd";
254    std::string srcStr = "abcdef";
255    std::string endStr = "def";
256    std::shared_ptr<StringHelp> stringHelp = std::make_shared<StringHelp>();
257    EXPECT_FALSE(stringHelp->EndsWith(input, suffix));
258    EXPECT_FALSE(stringHelp->EndsWithIgnoreCase(input, suffix));
259    bool result = stringHelp->EndsWith(srcStr, endStr);
260    EXPECT_TRUE(result);
261}
262
263HWTEST_F(TestUtils, FormatHelper001, TestSize.Level1) {
264    uint32_t height = 1280;
265    uint32_t width = 960;
266    std::shared_ptr<FormatHelper> formatHelper = std::make_shared<FormatHelper>();
267    uint32_t result = formatHelper->CalculateDataRowCount(height, IEffectFormat::YUVNV12);
268    ASSERT_EQ(result, height * YUV_BYTES_PER_PIXEL);
269
270    result = formatHelper->CalculateDataRowCount(height, IEffectFormat::DEFAULT);
271    ASSERT_EQ(result, height);
272
273    result = formatHelper->CalculateRowStride(width, IEffectFormat::YCRCB_P010);
274    ASSERT_EQ(result, width * P10_BYTES_PER_LUMA);
275
276    result = formatHelper->CalculateRowStride(width, IEffectFormat::DEFAULT);
277    ASSERT_EQ(result, width);
278}
279
280std::shared_ptr<void> AllocBuffer(size_t size)
281{
282    if (size <= 0 || size > MAX_ALLOC_SIZE) {
283        return nullptr;
284    }
285
286    void *buffer = malloc(size);
287    if (buffer == nullptr) {
288        return nullptr;
289    }
290
291    std::shared_ptr<void> bufferPtr(buffer, [](void *buffer) {
292        if (buffer != nullptr) {
293            free(buffer);
294        }
295    });
296    return bufferPtr;
297}
298
299FormatConverterInfo CreateConverterInfo(IEffectFormat format, void *addr, uint32_t rowStride)
300{
301    return {
302        .bufferInfo = {
303            .width_ = WIDTH,
304            .height_ = HEIGHT,
305            .len_ = FormatHelper::CalculateSize(WIDTH, HEIGHT, format),
306            .formatType_ = format,
307            .rowStride_ = rowStride,
308        },
309        .buffer = addr,
310    };
311}
312
313HWTEST_F(TestUtils, FormatHelper002, TestSize.Level1)
314{
315    std::unordered_set<IEffectFormat> formats = FormatHelper::GetAllSupportedFormats();
316    ASSERT_NE(formats.size(), 0);
317
318    ASSERT_TRUE(FormatHelper::IsSupportConvert(IEffectFormat::RGBA8888, IEffectFormat::YUVNV21));
319
320    std::shared_ptr<void> rgbaBuffer = AllocBuffer(FormatHelper::CalculateSize(WIDTH, HEIGHT, IEffectFormat::RGBA8888));
321    FormatConverterInfo rgbaConverterInfo = CreateConverterInfo(IEffectFormat::RGBA8888, rgbaBuffer.get(),
322        RGBA_BYTES_PER_PIXEL * WIDTH);
323    std::shared_ptr<void> nv12Buffer = AllocBuffer(FormatHelper::CalculateSize(WIDTH, HEIGHT, IEffectFormat::YUVNV12));
324    FormatConverterInfo nv12ConverterInfo = CreateConverterInfo(IEffectFormat::YUVNV12, nv12Buffer.get(), WIDTH);
325    std::shared_ptr<void> nv21Buffer = AllocBuffer(FormatHelper::CalculateSize(WIDTH, HEIGHT, IEffectFormat::YUVNV21));
326    FormatConverterInfo nv21ConverterInfo = CreateConverterInfo(IEffectFormat::YUVNV21, nv21Buffer.get(), WIDTH);
327
328    ErrorCode res = FormatHelper::ConvertFormat(rgbaConverterInfo, nv12ConverterInfo);
329    ASSERT_EQ(res, ErrorCode::SUCCESS);
330
331    res = FormatHelper::ConvertFormat(rgbaConverterInfo, nv21ConverterInfo);
332    ASSERT_EQ(res, ErrorCode::SUCCESS);
333
334    res = FormatHelper::ConvertFormat(nv12ConverterInfo, rgbaConverterInfo);
335    ASSERT_EQ(res, ErrorCode::SUCCESS);
336
337    res = FormatHelper::ConvertFormat(nv21ConverterInfo, rgbaConverterInfo);
338    ASSERT_EQ(res, ErrorCode::SUCCESS);
339
340    res = FormatHelper::ConvertFormat(nv12ConverterInfo, nv21ConverterInfo);
341    ASSERT_NE(res, ErrorCode::SUCCESS);
342}
343
344HWTEST_F(TestUtils, NativeCommonUtils001, TestSize.Level1) {
345    ImageEffect_Format ohFormatType = ImageEffect_Format::EFFECT_PIXEL_FORMAT_RGBA8888;
346    IEffectFormat formatType;
347    std::shared_ptr<NativeCommonUtils> nativeCommonUtils = std::make_shared<NativeCommonUtils>();
348    nativeCommonUtils->SwitchToFormatType(ohFormatType, formatType);
349    ASSERT_EQ(formatType, IEffectFormat::RGBA8888);
350
351    ohFormatType = ImageEffect_Format::EFFECT_PIXEL_FORMAT_UNKNOWN;
352    nativeCommonUtils->SwitchToFormatType(ohFormatType, formatType);
353    ASSERT_EQ(formatType, IEffectFormat::DEFAULT);
354}
355
356HWTEST_F(TestUtils, ErrorCode001, TestSize.Level1) {
357    ErrorCode code = ErrorCode::ERR_PERMISSION_DENIED;
358    std::string expected = "ERROR_PERMISSION_DENIED";
359    std::string actual = GetErrorName(code);
360    ASSERT_EQ(expected, actual);
361
362    code = ErrorCode::ERR_INPUT_NULL;
363    expected = "Unknow error type";
364    actual = GetErrorName(code);
365    ASSERT_EQ(expected, actual);
366}
367
368HWTEST_F(TestUtils, MemcpyHelperCopyData001, TestSize.Level1)
369{
370    MemoryData *src = new MemoryData();
371    MemoryData *dst = src;
372    MemcpyHelper::CopyData(src, dst);
373    EXPECT_EQ(src, dst);
374
375    dst = new MemoryData();
376    MemcpyHelper::CopyData(src, dst);
377    EXPECT_NE(src, dst);
378
379    delete src;
380    delete dst;
381}
382
383HWTEST_F(TestUtils, MemcpyHelperCopyData002, TestSize.Level1)
384{
385    std::shared_ptr<BufferInfo> bufferInfo = std::make_unique<BufferInfo>();
386    void *add = nullptr;
387    std::shared_ptr<ExtraInfo> extraInfo = std::make_unique<ExtraInfo>();
388    std::shared_ptr<EffectBuffer> src = std::make_unique<EffectBuffer>(bufferInfo, add, extraInfo);
389    std::shared_ptr<EffectBuffer> dst = src;
390
391    MemcpyHelper::CopyData(src.get(), dst.get());
392    EXPECT_EQ(src.get(), dst.get());
393}
394
395HWTEST_F(TestUtils, NativeCommonUtilsSwitchToOHEffectInfo001, TestSize.Level1)
396{
397    EffectInfo effectInfo;
398    std::shared_ptr<OH_EffectFilterInfo> ohFilterInfo = std::make_shared<OH_EffectFilterInfo>();
399    std::vector<IPType> ipType;
400    ipType.emplace_back(IPType::DEFAULT);
401    effectInfo.formats_.emplace(IEffectFormat::DEFAULT, ipType);
402
403    NativeCommonUtils::SwitchToOHEffectInfo(&effectInfo, ohFilterInfo.get());
404    ASSERT_NE(ohFilterInfo->supportedBufferTypes.size(), 1);
405    ASSERT_EQ(ohFilterInfo->supportedFormats.size(), 1);
406    ASSERT_EQ(*(ohFilterInfo->supportedFormats.begin()), ImageEffect_Format::EFFECT_PIXEL_FORMAT_UNKNOWN);
407}
408
409HWTEST_F(TestUtils, NativeCommonUtilsGetSupportedFormats001, TestSize.Level1)
410{
411    std::shared_ptr<OH_EffectFilterInfo> ohFilterInfo = nullptr;
412    uint32_t result = NativeCommonUtils::GetSupportedFormats(ohFilterInfo.get());
413    ASSERT_EQ(result, 0);
414
415    ohFilterInfo = std::make_shared<OH_EffectFilterInfo>();
416    ohFilterInfo->supportedFormats.emplace(ImageEffect_Format::EFFECT_PIXEL_FORMAT_YCRCB_P010);
417    result = NativeCommonUtils::GetSupportedFormats(ohFilterInfo.get());
418    ASSERT_EQ(result, 0);
419}
420
421
422HWTEST_F(TestUtils, NativeCommonUtilsConverStartResult001, TestSize.Level1)
423{
424    ErrorCode errorCode = ErrorCode::ERR_ALLOC_MEMORY_FAIL;
425    ImageEffect_ErrorCode result = NativeCommonUtils::ConvertStartResult(errorCode);
426    ASSERT_EQ(result, ImageEffect_ErrorCode::EFFECT_ALLOCATE_MEMORY_FAILED);
427}
428}
429}
430}
431}