1/*
2 * Copyright (c) 2022-2022 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 <cstdlib>
17#include <memory>
18#include <string>
19#include "gtest/gtest.h"
20#define private public
21#define protected public
22#include "pipeline/filters/demux/data_packer.h"
23
24using namespace testing::ext;
25
26namespace OHOS {
27namespace Media {
28namespace Test {
29using namespace OHOS::Media::Plugin;
30
31class TestDataPacker : public ::testing::Test {
32public:
33    std::shared_ptr<DataPacker> dataPacker;
34    void SetUp() override
35    {
36        dataPacker = std::make_shared<DataPacker>();
37    }
38
39    void TearDown() override
40    {
41    }
42};
43
44AVBufferPtr CreateBuffer(size_t size, uint64_t offset = 0)
45{
46    const uint8_t* data = (uint8_t*)"1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
47    auto buffer = std::make_shared<AVBuffer>();
48    buffer->AllocMemory(nullptr, size);
49    buffer->GetMemory()->Write(data + offset, size);
50    return buffer;
51}
52
53AVBufferPtr CreateEmptyBuffer(size_t size)
54{
55    auto buffer = std::make_shared<AVBuffer>();
56    buffer->AllocMemory(nullptr, size);
57    buffer->GetMemory()->Write((uint8_t*)"\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0", size);
58    return buffer;
59}
60
61HWTEST_F(TestDataPacker, can_push_one_buffer_to_datapacker, TestSize.Level1)
62{
63    auto bufferPtr = CreateBuffer(10);
64    dataPacker->PushData(bufferPtr, 0);
65    ASSERT_STREQ("DataPacker (offset 0, size 10, buffer count 1)", dataPacker->ToString().c_str());
66}
67
68HWTEST_F(TestDataPacker, can_push_two_buffers_to_datapacker, TestSize.Level1)
69{
70    auto bufferPtr = CreateBuffer(10);
71    dataPacker->PushData(bufferPtr, 0);
72    auto bufferPtr2 = CreateBuffer(4, 10);
73    dataPacker->PushData(bufferPtr2, 10);
74    ASSERT_STREQ("DataPacker (offset 0, size 14, buffer count 2)", dataPacker->ToString().c_str());
75}
76
77HWTEST_F(TestDataPacker, should_return_true_if_check_range_in_datapacker, TestSize.Level1)
78{
79    auto bufferPtr = CreateBuffer(10);
80    dataPacker->PushData(bufferPtr, 0);
81    uint64_t curOffset = 0;
82    ASSERT_TRUE(dataPacker->IsDataAvailable(3, 2, curOffset));
83    ASSERT_EQ(curOffset, 10);
84}
85
86HWTEST_F(TestDataPacker, should_return_false_if_check_range_not_in_datapacker, TestSize.Level1)
87{
88    auto bufferPtr = CreateBuffer(10);
89    dataPacker->PushData(bufferPtr, 0);
90    uint64_t curOffset = 0;
91    ASSERT_FALSE(dataPacker->IsDataAvailable(11, 2, curOffset));
92}
93
94HWTEST_F(TestDataPacker, should_update_offset_to_get_range_offset_if_start_not_in_datapacker, TestSize.Level1)
95{
96    auto bufferPtr = CreateBuffer(10);
97    dataPacker->PushData(bufferPtr, 0);
98    uint64_t curOffset = 0;
99    ASSERT_FALSE(dataPacker->IsDataAvailable(11, 2, curOffset));
100    ASSERT_EQ(curOffset, 11);
101}
102
103HWTEST_F(TestDataPacker, should_update_offset_to_datapacker_offset_end_if_start_in_datapacker, TestSize.Level1)
104{
105    auto bufferPtr = CreateBuffer(10);
106    dataPacker->PushData(bufferPtr, 0);
107    uint64_t curOffset = 0;
108    ASSERT_FALSE(dataPacker->IsDataAvailable(8, 10, curOffset));
109    ASSERT_EQ(curOffset, 10);
110}
111
112HWTEST_F(TestDataPacker, can_get_data_in_the_middle_of_one_buffer, TestSize.Level1)
113{
114    auto bufferPtr = CreateBuffer(10);
115    dataPacker->PushData(bufferPtr, 0);
116    ASSERT_STREQ("DataPacker (offset 0, size 10, buffer count 1)", dataPacker->ToString().c_str());
117    uint64_t curOffset = 0;
118    ASSERT_TRUE(dataPacker->IsDataAvailable(3, 2, curOffset));
119    ASSERT_EQ(curOffset, 10);
120    auto bufferOut = CreateEmptyBuffer(3);
121    dataPacker->GetRange(3, 2, bufferOut);
122    ASSERT_STREQ("45", (const char *)(bufferOut->GetMemory()->GetReadOnlyData()));
123}
124
125HWTEST_F(TestDataPacker, remove_old_data_after_second_get_range, TestSize.Level1)
126{
127    auto bufferPtr = CreateBuffer(10);
128    dataPacker->PushData(bufferPtr, 0);
129    ASSERT_STREQ("DataPacker (offset 0, size 10, buffer count 1)", dataPacker->ToString().c_str());
130    uint64_t curOffset = 0;
131    ASSERT_TRUE(dataPacker->IsDataAvailable(3, 2, curOffset));
132    ASSERT_EQ(curOffset, 10);
133    auto bufferOut = CreateEmptyBuffer(5);
134    dataPacker->GetRange(3, 4, bufferOut);
135    bufferOut->GetMemory()->UpdateDataSize(0);
136    dataPacker->GetRange(5, 2, bufferOut);
137    ASSERT_STREQ("DataPacker (offset 5, size 5, buffer count 1)", dataPacker->ToString().c_str());
138}
139
140HWTEST_F(TestDataPacker, remove_old_data_after_second_get_range_when_two_buffers_in_datapacker, TestSize.Level1)
141{
142    auto bufferPtr = CreateBuffer(10);
143    dataPacker->PushData(bufferPtr, 0);
144    auto bufferPtr2 = CreateBuffer(4, 10);
145    dataPacker->PushData(bufferPtr2, 10);
146    ASSERT_STREQ("DataPacker (offset 0, size 14, buffer count 2)", dataPacker->ToString().c_str());
147
148    auto bufferOut = CreateEmptyBuffer(5);
149    dataPacker->GetRange(3, 4, bufferOut);
150    ASSERT_STREQ("DataPacker (offset 0, size 14, buffer count 2)", dataPacker->ToString().c_str());
151
152    bufferOut->GetMemory()->UpdateDataSize(0);
153    dataPacker->GetRange(11, 2, bufferOut);
154    ASSERT_STREQ("DataPacker (offset 11, size 3, buffer count 1)", dataPacker->ToString().c_str());
155}
156HWTEST_F(TestDataPacker, can_get_data_from_two_buffers, TestSize.Level1)
157{
158    auto bufferPtr = CreateBuffer(10);
159    dataPacker->PushData(bufferPtr, 0);
160    uint64_t curOffset = 0;
161    ASSERT_FALSE(dataPacker->IsDataAvailable(0, 15, curOffset));
162    ASSERT_EQ(curOffset, 10);
163    auto bufferPtr2 = CreateBuffer(10, curOffset);
164    dataPacker->PushData(bufferPtr2, curOffset);
165    auto bufferOut = CreateEmptyBuffer(16);
166    ASSERT_TRUE(dataPacker->GetRange(0, 15, bufferOut));
167    ASSERT_EQ(15, bufferOut->GetMemory()->GetSize());
168    ASSERT_STREQ("1234567890abcde", (const char*)(bufferOut->GetMemory()->GetReadOnlyData()));
169}
170} // namespace Test
171} // namespace Media
172} // namespace OHOS