1 /*
2 * Copyright (C) 2019 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #define LOG_TAG "InternalStreamManagerTests"
18 #include <log/log.h>
19
20 #include <gtest/gtest.h>
21 #include <hal_types.h>
22 #include <hardware/gralloc.h>
23 #include <internal_stream_manager.h>
24
25 namespace android {
26 namespace google_camera_hal {
27
28 static const uint32_t kDataBytes = 256;
29 static const uint32_t kNumEntries = 10;
30
31 // Preview stream template used in the test.
32 static constexpr Stream kPreviewStreamTemplate{
33 .stream_type = StreamType::kOutput,
34 .width = 1920,
35 .height = 1080,
36 .format = HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED,
37 .usage = GRALLOC_USAGE_HW_TEXTURE,
38 .rotation = StreamRotation::kRotation0,
39 };
40
41 // Video stream template used in the test.
42 static constexpr Stream kVideoStreamTemplate{
43 .stream_type = StreamType::kOutput,
44 .width = 3840,
45 .height = 2160,
46 .format = HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED,
47 .usage = GRALLOC_USAGE_HW_VIDEO_ENCODER,
48 .rotation = StreamRotation::kRotation0,
49 };
50
51 // Raw stream template used in the test.
52 static constexpr Stream kRawStreamTemplate{
53 .stream_type = StreamType::kOutput,
54 .width = 4022,
55 .height = 3024,
56 .format = HAL_PIXEL_FORMAT_RAW10,
57 .usage = 0,
58 .rotation = StreamRotation::kRotation0,
59 };
60
61 // Preview HAL stream template used in the test.
62 static constexpr HalStream kPreviewHalStreamTemplate{
63 .override_format = HAL_PIXEL_FORMAT_YV12,
64 .producer_usage = GRALLOC_USAGE_HW_CAMERA_WRITE,
65 .max_buffers = 4,
66 };
67
68 // Video HAL stream template used in the test.
69 static constexpr HalStream kVideoHalStreamTemplate{
70 .override_format = HAL_PIXEL_FORMAT_YV12,
71 .producer_usage = GRALLOC_USAGE_HW_CAMERA_WRITE,
72 .max_buffers = 4,
73 };
74
75 // Raw HAL stream template used in the test.
76 static constexpr HalStream kRawHalStreamTemplate{
77 .override_format = HAL_PIXEL_FORMAT_RAW10,
78 .producer_usage = GRALLOC_USAGE_HW_CAMERA_WRITE,
79 .max_buffers = 16,
80 };
81
82 // Additional number of buffers to allocate.
83 static constexpr uint32_t kNumAdditionalBuffers = 2;
84
SetMetadata(std::unique_ptr<HalCameraMetadata> & hal_metadata)85 static void SetMetadata(std::unique_ptr<HalCameraMetadata>& hal_metadata) {
86 // Set current BOOT_TIME timestamp in nanoseconds
87 struct timespec ts;
88 if (clock_gettime(CLOCK_BOOTTIME, &ts) == 0) {
89 static const int64_t kNsPerSec = 1000000000;
90 int64_t buffer_timestamp = ts.tv_sec * kNsPerSec + ts.tv_nsec;
91 status_t res =
92 hal_metadata->Set(ANDROID_SENSOR_TIMESTAMP, &buffer_timestamp, 1);
93 ASSERT_EQ(res, OK) << "Set ANDROID_SENSOR_TIMESTAMP failed";
94 }
95 }
96
TEST(InternalStreamManagerTests,Create)97 TEST(InternalStreamManagerTests, Create) {
98 auto stream_manager = InternalStreamManager::Create();
99 EXPECT_NE(stream_manager, nullptr);
100 }
101
TEST(InternalStreamManagerTests,RegisterNewInternalStream)102 TEST(InternalStreamManagerTests, RegisterNewInternalStream) {
103 auto stream_manager = InternalStreamManager::Create();
104 ASSERT_NE(stream_manager, nullptr);
105
106 EXPECT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
107 /*stream_id=*/nullptr),
108 BAD_VALUE)
109 << "Passing a nullptr stream should fail";
110
111 int32_t preview_stream_id = -1;
112 int32_t video_stream_id = -1;
113
114 EXPECT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
115 &preview_stream_id),
116 OK);
117 EXPECT_EQ(stream_manager->RegisterNewInternalStream(kVideoStreamTemplate,
118 &video_stream_id),
119 OK);
120 EXPECT_NE(preview_stream_id, video_stream_id);
121 }
122
TEST(InternalStreamManagerTests,AllocateBuffers)123 TEST(InternalStreamManagerTests, AllocateBuffers) {
124 auto stream_manager = InternalStreamManager::Create();
125 ASSERT_NE(stream_manager, nullptr);
126
127 HalStream preview_hal_stream = kPreviewHalStreamTemplate;
128 HalStream video_hal_stream = kVideoHalStreamTemplate;
129
130 EXPECT_NE(stream_manager->AllocateBuffers(preview_hal_stream), OK)
131 << "Allocating buffers for unregistered stream should fail";
132
133 // Allocate preview and video stream.
134 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
135 &preview_hal_stream.id),
136 OK);
137 EXPECT_EQ(stream_manager->AllocateBuffers(preview_hal_stream), OK);
138
139 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kVideoStreamTemplate,
140 &video_hal_stream.id),
141 OK);
142 EXPECT_EQ(stream_manager->AllocateBuffers(video_hal_stream), OK);
143
144 EXPECT_NE(stream_manager->AllocateBuffers(preview_hal_stream), OK)
145 << "Allocating buffers for the same stream again should fail";
146
147 stream_manager->FreeStream(preview_hal_stream.id);
148 EXPECT_NE(stream_manager->AllocateBuffers(preview_hal_stream), OK)
149 << "Allocating buffers for a freed stream should fail";
150 }
151
TEST(InternalStreamManagerTests,FreeStream)152 TEST(InternalStreamManagerTests, FreeStream) {
153 auto stream_manager = InternalStreamManager::Create();
154 ASSERT_NE(stream_manager, nullptr);
155
156 HalStream preview_hal_stream = kPreviewHalStreamTemplate;
157
158 // Free an invalid stream.
159 stream_manager->FreeStream(/*stream_id=*/-1);
160
161 // Free a registered stream.
162 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
163 &preview_hal_stream.id),
164 OK);
165 stream_manager->FreeStream(preview_hal_stream.id);
166
167 // Free an allocated stream.
168 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
169 &preview_hal_stream.id),
170 OK);
171 ASSERT_EQ(stream_manager->AllocateBuffers(preview_hal_stream), OK);
172 stream_manager->FreeStream(preview_hal_stream.id);
173 }
174
TEST(InternalStreamManagerTests,GetStreamBuffer)175 TEST(InternalStreamManagerTests, GetStreamBuffer) {
176 auto stream_manager = InternalStreamManager::Create();
177 ASSERT_NE(stream_manager, nullptr);
178
179 HalStream preview_hal_stream = kPreviewHalStreamTemplate;
180
181 // Get buffer from an invalid stream.
182 StreamBuffer dummy_buffer;
183 EXPECT_NE(stream_manager->GetStreamBuffer(/*stream_id=*/-1, &dummy_buffer), OK)
184 << "Getting a buffer from an invalid stream should fail";
185
186 // Register and allocate buffers.
187 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
188 &preview_hal_stream.id),
189 OK);
190 ASSERT_EQ(stream_manager->AllocateBuffers(preview_hal_stream,
191 kNumAdditionalBuffers),
192 OK);
193
194 EXPECT_NE(stream_manager->GetStreamBuffer(preview_hal_stream.id, nullptr), OK)
195 << "Getting a buffer with nullptr should fail";
196
197 // Verify we can get a number of buffers we allocated.
198 uint32_t num_buffers = preview_hal_stream.max_buffers + kNumAdditionalBuffers;
199 std::vector<StreamBuffer> buffers(num_buffers);
200 for (auto& buffer : buffers) {
201 EXPECT_EQ(stream_manager->GetStreamBuffer(preview_hal_stream.id, &buffer),
202 OK);
203 EXPECT_NE(buffer.buffer, kInvalidBufferHandle) << "Buffer should be valid";
204 }
205 }
206
TEST(InternalStreamManagerTests,ReturnStreamBuffer)207 TEST(InternalStreamManagerTests, ReturnStreamBuffer) {
208 auto stream_manager = InternalStreamManager::Create();
209 ASSERT_NE(stream_manager, nullptr);
210
211 HalStream preview_hal_stream = kPreviewHalStreamTemplate;
212
213 // Register and allocate buffers.
214 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
215 &preview_hal_stream.id),
216 OK);
217 ASSERT_EQ(stream_manager->AllocateBuffers(preview_hal_stream), OK);
218
219 // Get all buffers.
220 std::vector<StreamBuffer> buffers(preview_hal_stream.max_buffers);
221 for (auto& buffer : buffers) {
222 ASSERT_EQ(stream_manager->GetStreamBuffer(preview_hal_stream.id, &buffer),
223 OK);
224 }
225
226 // Return all buffers.
227 for (auto& buffer : buffers) {
228 EXPECT_EQ(stream_manager->ReturnStreamBuffer(buffer), OK);
229 }
230
231 EXPECT_NE(stream_manager->ReturnStreamBuffer(buffers[0]), OK)
232 << "Returning the same buffer again should fail";
233
234 StreamBuffer invalid_buffer = {
235 .stream_id = -1,
236 };
237 EXPECT_NE(stream_manager->ReturnStreamBuffer(invalid_buffer), OK)
238 << "Returning a invalid buffer should fail";
239 }
240
TEST(InternalStreamManagerTests,ReturnFilledBuffer)241 TEST(InternalStreamManagerTests, ReturnFilledBuffer) {
242 auto stream_manager = InternalStreamManager::Create();
243 ASSERT_NE(stream_manager, nullptr);
244
245 HalStream preview_hal_stream = kPreviewHalStreamTemplate;
246
247 // Register and allocate buffers.
248 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kPreviewStreamTemplate,
249 &preview_hal_stream.id),
250 OK);
251 ASSERT_EQ(stream_manager->AllocateBuffers(preview_hal_stream), OK);
252
253 // Get all buffers.
254 std::vector<StreamBuffer> buffers(preview_hal_stream.max_buffers);
255 for (auto& buffer : buffers) {
256 ASSERT_EQ(stream_manager->GetStreamBuffer(preview_hal_stream.id, &buffer),
257 OK);
258 }
259
260 // Return all filled buffers and metadata.
261 uint32_t frame_number = 1;
262 int32_t invalid_stream_id = -1;
263 for (auto& buffer : buffers) {
264 auto metadata = HalCameraMetadata::Create(kNumEntries, kDataBytes);
265 EXPECT_EQ(stream_manager->ReturnFilledBuffer(frame_number, buffer), OK);
266 // Return invalid stream id will return BAD_VALUE
267 EXPECT_EQ(stream_manager->ReturnMetadata(invalid_stream_id, frame_number,
268 metadata.get()),
269 BAD_VALUE);
270 EXPECT_EQ(stream_manager->ReturnMetadata(preview_hal_stream.id,
271 frame_number, metadata.get()),
272 OK);
273 frame_number++;
274 }
275 }
276
TEST(InternalStreamManagerTests,GetMostRecentStreamBuffer)277 TEST(InternalStreamManagerTests, GetMostRecentStreamBuffer) {
278 auto stream_manager = InternalStreamManager::Create();
279 ASSERT_NE(stream_manager, nullptr);
280
281 HalStream raw_hal_stream = kRawHalStreamTemplate;
282
283 // Register and allocate buffers.
284 ASSERT_EQ(stream_manager->RegisterNewInternalStream(kRawStreamTemplate,
285 &raw_hal_stream.id),
286 OK);
287 ASSERT_EQ(stream_manager->AllocateBuffers(raw_hal_stream), OK);
288
289 StreamBuffer stream_buffer[kRawHalStreamTemplate.max_buffers];
290 uint32_t frame_index = 0;
291 status_t res;
292 // Get empty buffer and then fill buffer and metadata
293 for (uint32_t i = 0; i < kRawHalStreamTemplate.max_buffers; i++) {
294 ASSERT_EQ(
295 stream_manager->GetStreamBuffer(raw_hal_stream.id, &stream_buffer[i]),
296 OK);
297
298 res = stream_manager->ReturnFilledBuffer(frame_index, stream_buffer[i]);
299 ASSERT_EQ(res, OK) << "ReturnFilledBuffer failed: " << strerror(res);
300
301 auto metadata = HalCameraMetadata::Create(kNumEntries, kDataBytes);
302 SetMetadata(metadata);
303 res = stream_manager->ReturnMetadata(raw_hal_stream.id, frame_index,
304 metadata.get());
305 ASSERT_EQ(res, OK) << "ReturnMetadata failed: " << strerror(res);
306 frame_index++;
307 }
308
309 std::vector<StreamBuffer> input_buffers;
310 std::vector<std::unique_ptr<HalCameraMetadata>> input_buffer_metadata;
311 res = stream_manager->GetMostRecentStreamBuffer(
312 raw_hal_stream.id, &input_buffers, &input_buffer_metadata,
313 /*payload_frames*/ 1);
314 ASSERT_EQ(res, OK) << "GetMostRecentZslBuffers failed.";
315
316 // Pending buffer is not empty after call GetMostRecentStreamBuffer
317 bool empty = stream_manager->IsPendingBufferEmpty(raw_hal_stream.id);
318 ASSERT_EQ(empty, false) << "Pending buffer is empty";
319
320 res = stream_manager->ReturnZslStreamBuffers(frame_index, raw_hal_stream.id);
321 ASSERT_EQ(res, OK) << "ReturnZslStreamBuffers failed.";
322
323 // Pending buffer is empty after call ReturnZslStreamBuffers
324 empty = stream_manager->IsPendingBufferEmpty(raw_hal_stream.id);
325 ASSERT_EQ(empty, true) << "Pending buffer is not empty";
326 }
327
328 } // namespace google_camera_hal
329 } // namespace android
330