blob: 1f5867adb62823f3bd7c53c06e616bfbc474994a [file] [log] [blame]
Igor Murashkin634a5152013-02-20 17:15:11 -08001/*
2 * Copyright (C) 2013 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#include <gtest/gtest.h>
18#include <iostream>
19
Igor Murashkin53765732013-02-20 17:41:57 -080020#include <binder/IPCThreadState.h>
21#include <utils/Thread.h>
22
Igor Murashkin634a5152013-02-20 17:15:11 -080023#include "Camera.h"
24#include "ProCamera.h"
Igor Murashkin53765732013-02-20 17:41:57 -080025#include <utils/Vector.h>
26#include <utils/Mutex.h>
27#include <utils/Condition.h>
Igor Murashkin634a5152013-02-20 17:15:11 -080028
Igor Murashkin68506fd2013-02-20 17:57:31 -080029#include <gui/SurfaceComposerClient.h>
30#include <gui/Surface.h>
31
32#include <system/camera_metadata.h>
33#include <hardware/camera2.h> // for CAMERA2_TEMPLATE_PREVIEW only
Igor Murashkindcb07d52013-02-21 14:18:10 -080034#include <camera/CameraMetadata.h>
Igor Murashkin68506fd2013-02-20 17:57:31 -080035
Igor Murashkinbfc99152013-02-27 12:55:20 -080036#include <camera/ICameraServiceListener.h>
37
Igor Murashkin634a5152013-02-20 17:15:11 -080038namespace android {
39namespace camera2 {
40namespace tests {
41namespace client {
42
43#define CAMERA_ID 0
44#define TEST_DEBUGGING 0
45
Igor Murashkin68506fd2013-02-20 17:57:31 -080046#define TEST_LISTENER_TIMEOUT 1000000000 // 1 second listener timeout
Igor Murashkin5835cc42013-02-20 19:29:53 -080047#define TEST_FORMAT HAL_PIXEL_FORMAT_Y16 //TODO: YUY2 instead
48
Igor Murashkineb72e172013-02-21 11:43:14 -080049#define TEST_FORMAT_MAIN HAL_PIXEL_FORMAT_Y8
Igor Murashkin5835cc42013-02-20 19:29:53 -080050#define TEST_FORMAT_DEPTH HAL_PIXEL_FORMAT_Y16
51
Igor Murashkindcb07d52013-02-21 14:18:10 -080052// defaults for display "test"
Igor Murashkinbfc99152013-02-27 12:55:20 -080053#define TEST_DISPLAY_FORMAT HAL_PIXEL_FORMAT_Y8
54#define TEST_DISPLAY_WIDTH 320
55#define TEST_DISPLAY_HEIGHT 240
Igor Murashkindcb07d52013-02-21 14:18:10 -080056
Igor Murashkin5835cc42013-02-20 19:29:53 -080057#define TEST_CPU_FRAME_COUNT 2
58#define TEST_CPU_HEAP_COUNT 5
Igor Murashkin53765732013-02-20 17:41:57 -080059
Igor Murashkin4bc4a382013-02-20 13:36:17 -080060#define TEST_FRAME_PROCESSING_DELAY_US 200000 // 200 ms
61
Igor Murashkin634a5152013-02-20 17:15:11 -080062#if TEST_DEBUGGING
63#define dout std::cerr
64#else
65#define dout if (0) std::cerr
66#endif
67
Igor Murashkin39f79f72013-01-30 10:14:24 -080068#define EXPECT_OK(x) EXPECT_EQ(OK, (x))
69#define ASSERT_OK(x) ASSERT_EQ(OK, (x))
70
71class ProCameraTest;
72
Igor Murashkinbfc99152013-02-27 12:55:20 -080073struct ServiceListener : public BnCameraServiceListener {
74
75 ServiceListener() :
76 mLatestStatus(STATUS_UNKNOWN),
77 mPrevStatus(STATUS_UNKNOWN)
78 {
79 }
80
81 void onStatusChanged(Status status, int32_t cameraId) {
82 dout << "On status changed: 0x" << std::hex
Igor Murashkinc6deb682013-04-18 11:53:35 -070083 << (unsigned int) status << " cameraId " << cameraId
Igor Murashkinbfc99152013-02-27 12:55:20 -080084 << std::endl;
85
86 Mutex::Autolock al(mMutex);
87
88 mLatestStatus = status;
89 mCondition.broadcast();
90 }
91
92 status_t waitForStatusChange(Status& newStatus) {
93 Mutex::Autolock al(mMutex);
94
95 if (mLatestStatus != mPrevStatus) {
96 newStatus = mLatestStatus;
97 mPrevStatus = mLatestStatus;
98 return OK;
99 }
100
101 status_t stat = mCondition.waitRelative(mMutex,
102 TEST_LISTENER_TIMEOUT);
103
104 if (stat == OK) {
105 newStatus = mLatestStatus;
106 mPrevStatus = mLatestStatus;
107 }
108
109 return stat;
110 }
111
112 Condition mCondition;
113 Mutex mMutex;
114
115 Status mLatestStatus;
116 Status mPrevStatus;
117};
118
Igor Murashkin5835cc42013-02-20 19:29:53 -0800119enum ProEvent {
Igor Murashkin53765732013-02-20 17:41:57 -0800120 UNKNOWN,
121 ACQUIRED,
122 RELEASED,
Igor Murashkin5835cc42013-02-20 19:29:53 -0800123 STOLEN,
Igor Murashkinc6deb682013-04-18 11:53:35 -0700124 FRAME_RECEIVED,
Igor Murashkina91537e2013-02-21 12:02:29 -0800125 RESULT_RECEIVED,
Igor Murashkin53765732013-02-20 17:41:57 -0800126};
127
Igor Murashkina91537e2013-02-21 12:02:29 -0800128inline int ProEvent_Mask(ProEvent e) {
129 return (1 << static_cast<int>(e));
130}
131
Igor Murashkin5835cc42013-02-20 19:29:53 -0800132typedef Vector<ProEvent> EventList;
Igor Murashkin53765732013-02-20 17:41:57 -0800133
134class ProCameraTestThread : public Thread
135{
136public:
137 ProCameraTestThread() {
138 }
139
140 virtual bool threadLoop() {
141 mProc = ProcessState::self();
142 mProc->startThreadPool();
143
144 IPCThreadState *ptr = IPCThreadState::self();
145
Igor Murashkin53765732013-02-20 17:41:57 -0800146 ptr->joinThreadPool();
Igor Murashkin53765732013-02-20 17:41:57 -0800147
148 return false;
149 }
150
151 sp<ProcessState> mProc;
152};
153
154class ProCameraTestListener : public ProCameraListener {
155
156public:
Igor Murashkina91537e2013-02-21 12:02:29 -0800157 static const int EVENT_MASK_ALL = 0xFFFFFFFF;
158
159 ProCameraTestListener() {
160 mEventMask = EVENT_MASK_ALL;
Igor Murashkinc6deb682013-04-18 11:53:35 -0700161 mDropFrames = false;
Igor Murashkina91537e2013-02-21 12:02:29 -0800162 }
163
Igor Murashkin53765732013-02-20 17:41:57 -0800164 status_t WaitForEvent() {
165 Mutex::Autolock cal(mConditionMutex);
166
167 {
168 Mutex::Autolock al(mListenerMutex);
169
Igor Murashkin5835cc42013-02-20 19:29:53 -0800170 if (mProEventList.size() > 0) {
Igor Murashkin53765732013-02-20 17:41:57 -0800171 return OK;
172 }
173 }
174
175 return mListenerCondition.waitRelative(mConditionMutex,
176 TEST_LISTENER_TIMEOUT);
177 }
178
179 /* Read events into out. Existing queue is flushed */
180 void ReadEvents(EventList& out) {
181 Mutex::Autolock al(mListenerMutex);
182
Igor Murashkin5835cc42013-02-20 19:29:53 -0800183 for (size_t i = 0; i < mProEventList.size(); ++i) {
184 out.push(mProEventList[i]);
Igor Murashkin53765732013-02-20 17:41:57 -0800185 }
186
Igor Murashkin5835cc42013-02-20 19:29:53 -0800187 mProEventList.clear();
Igor Murashkin53765732013-02-20 17:41:57 -0800188 }
189
190 /**
191 * Dequeue 1 event from the event queue.
192 * Returns UNKNOWN if queue is empty
193 */
Igor Murashkin5835cc42013-02-20 19:29:53 -0800194 ProEvent ReadEvent() {
Igor Murashkin53765732013-02-20 17:41:57 -0800195 Mutex::Autolock al(mListenerMutex);
196
Igor Murashkin5835cc42013-02-20 19:29:53 -0800197 if (mProEventList.size() == 0) {
Igor Murashkin53765732013-02-20 17:41:57 -0800198 return UNKNOWN;
199 }
200
Igor Murashkin5835cc42013-02-20 19:29:53 -0800201 ProEvent ev = mProEventList[0];
202 mProEventList.removeAt(0);
Igor Murashkin53765732013-02-20 17:41:57 -0800203
204 return ev;
205 }
206
Igor Murashkina91537e2013-02-21 12:02:29 -0800207 void SetEventMask(int eventMask) {
208 Mutex::Autolock al(mListenerMutex);
209 mEventMask = eventMask;
210 }
211
Igor Murashkinc6deb682013-04-18 11:53:35 -0700212 // Automatically acquire/release frames as they are available
213 void SetDropFrames(bool dropFrames) {
214 Mutex::Autolock al(mListenerMutex);
215 mDropFrames = dropFrames;
216 }
217
Igor Murashkin53765732013-02-20 17:41:57 -0800218private:
Igor Murashkin5835cc42013-02-20 19:29:53 -0800219 void QueueEvent(ProEvent ev) {
Igor Murashkina91537e2013-02-21 12:02:29 -0800220 bool eventAdded = false;
Igor Murashkin53765732013-02-20 17:41:57 -0800221 {
222 Mutex::Autolock al(mListenerMutex);
Igor Murashkina91537e2013-02-21 12:02:29 -0800223
Igor Murashkinc6deb682013-04-18 11:53:35 -0700224 // Drop events not part of mask
Igor Murashkina91537e2013-02-21 12:02:29 -0800225 if (ProEvent_Mask(ev) & mEventMask) {
226 mProEventList.push(ev);
227 eventAdded = true;
228 }
Igor Murashkin53765732013-02-20 17:41:57 -0800229 }
230
Igor Murashkina91537e2013-02-21 12:02:29 -0800231 if (eventAdded) {
232 mListenerCondition.broadcast();
233 }
Igor Murashkin53765732013-02-20 17:41:57 -0800234 }
235
236protected:
237
238 //////////////////////////////////////////////////
239 ///////// ProCameraListener //////////////////////
240 //////////////////////////////////////////////////
241
242
243 // Lock has been acquired. Write operations now available.
244 virtual void onLockAcquired() {
245 QueueEvent(ACQUIRED);
246 }
247 // Lock has been released with exclusiveUnlock
248 virtual void onLockReleased() {
249 QueueEvent(RELEASED);
250 }
251
252 // Lock has been stolen by another client.
253 virtual void onLockStolen() {
254 QueueEvent(STOLEN);
255 }
256
257 // Lock free.
258 virtual void onTriggerNotify(int32_t ext1, int32_t ext2, int32_t ext3) {
259
260 dout << "Trigger notify: " << ext1 << " " << ext2
261 << " " << ext3 << std::endl;
262 }
263
Igor Murashkinc6deb682013-04-18 11:53:35 -0700264 virtual void onFrameAvailable(int streamId,
265 const sp<CpuConsumer>& consumer) {
Igor Murashkin5835cc42013-02-20 19:29:53 -0800266
Igor Murashkinc6deb682013-04-18 11:53:35 -0700267 QueueEvent(FRAME_RECEIVED);
Igor Murashkin5835cc42013-02-20 19:29:53 -0800268
Igor Murashkinc6deb682013-04-18 11:53:35 -0700269 Mutex::Autolock al(mListenerMutex);
270 if (mDropFrames) {
271 CpuConsumer::LockedBuffer buf;
272 status_t ret;
Igor Murashkin5835cc42013-02-20 19:29:53 -0800273
Igor Murashkinc6deb682013-04-18 11:53:35 -0700274 if (OK == (ret = consumer->lockNextBuffer(&buf))) {
275
276 dout << "Frame received on streamId = " << streamId <<
277 ", dataPtr = " << (void*)buf.data <<
278 ", timestamp = " << buf.timestamp << std::endl;
279
280 EXPECT_OK(consumer->unlockBuffer(buf));
281 }
282 } else {
283 dout << "Frame received on streamId = " << streamId << std::endl;
284 }
Igor Murashkin5835cc42013-02-20 19:29:53 -0800285 }
Igor Murashkinc6deb682013-04-18 11:53:35 -0700286
Eino-Ville Talvalaf1e98d82013-09-06 09:32:43 -0700287 virtual void onResultReceived(int32_t requestId,
Igor Murashkina91537e2013-02-21 12:02:29 -0800288 camera_metadata* request) {
Eino-Ville Talvalaf1e98d82013-09-06 09:32:43 -0700289 dout << "Result received requestId = " << requestId
Igor Murashkina91537e2013-02-21 12:02:29 -0800290 << ", requestPtr = " << (void*)request << std::endl;
291 QueueEvent(RESULT_RECEIVED);
Igor Murashkin5835cc42013-02-20 19:29:53 -0800292 free_camera_metadata(request);
293 }
294
Igor Murashkinfa4cf9d2013-03-04 16:14:23 -0800295 virtual void notify(int32_t msg, int32_t ext1, int32_t ext2) {
296 dout << "Notify received: msg " << std::hex << msg
297 << ", ext1: " << std::hex << ext1 << ", ext2: " << std::hex << ext2
298 << std::endl;
299 }
Igor Murashkin53765732013-02-20 17:41:57 -0800300
Igor Murashkin5835cc42013-02-20 19:29:53 -0800301 Vector<ProEvent> mProEventList;
Igor Murashkin53765732013-02-20 17:41:57 -0800302 Mutex mListenerMutex;
303 Mutex mConditionMutex;
304 Condition mListenerCondition;
Igor Murashkina91537e2013-02-21 12:02:29 -0800305 int mEventMask;
Igor Murashkinc6deb682013-04-18 11:53:35 -0700306 bool mDropFrames;
Igor Murashkin53765732013-02-20 17:41:57 -0800307};
308
Igor Murashkin634a5152013-02-20 17:15:11 -0800309class ProCameraTest : public ::testing::Test {
310
Igor Murashkin53765732013-02-20 17:41:57 -0800311public:
312 ProCameraTest() {
Igor Murashkindcb07d52013-02-21 14:18:10 -0800313 char* displaySecsEnv = getenv("TEST_DISPLAY_SECS");
314 if (displaySecsEnv != NULL) {
315 mDisplaySecs = atoi(displaySecsEnv);
316 if (mDisplaySecs < 0) {
317 mDisplaySecs = 0;
318 }
319 } else {
320 mDisplaySecs = 0;
321 }
322
323 char* displayFmtEnv = getenv("TEST_DISPLAY_FORMAT");
324 if (displayFmtEnv != NULL) {
325 mDisplayFmt = FormatFromString(displayFmtEnv);
326 } else {
327 mDisplayFmt = TEST_DISPLAY_FORMAT;
328 }
329
330 char* displayWidthEnv = getenv("TEST_DISPLAY_WIDTH");
331 if (displayWidthEnv != NULL) {
332 mDisplayW = atoi(displayWidthEnv);
333 if (mDisplayW < 0) {
334 mDisplayW = 0;
335 }
336 } else {
337 mDisplayW = TEST_DISPLAY_WIDTH;
338 }
339
340 char* displayHeightEnv = getenv("TEST_DISPLAY_HEIGHT");
341 if (displayHeightEnv != NULL) {
342 mDisplayH = atoi(displayHeightEnv);
343 if (mDisplayH < 0) {
344 mDisplayH = 0;
345 }
346 } else {
347 mDisplayH = TEST_DISPLAY_HEIGHT;
348 }
Igor Murashkin53765732013-02-20 17:41:57 -0800349 }
350
Igor Murashkin39f79f72013-01-30 10:14:24 -0800351 static void SetUpTestCase() {
352 // Binder Thread Pool Initialization
Igor Murashkin53765732013-02-20 17:41:57 -0800353 mTestThread = new ProCameraTestThread();
354 mTestThread->run("ProCameraTestThread");
Igor Murashkin39f79f72013-01-30 10:14:24 -0800355 }
Igor Murashkin53765732013-02-20 17:41:57 -0800356
Igor Murashkin39f79f72013-01-30 10:14:24 -0800357 virtual void SetUp() {
Igor Murashkin634a5152013-02-20 17:15:11 -0800358 mCamera = ProCamera::connect(CAMERA_ID);
359 ASSERT_NE((void*)NULL, mCamera.get());
Igor Murashkin53765732013-02-20 17:41:57 -0800360
361 mListener = new ProCameraTestListener();
362 mCamera->setListener(mListener);
Igor Murashkin634a5152013-02-20 17:15:11 -0800363 }
364
365 virtual void TearDown() {
366 ASSERT_NE((void*)NULL, mCamera.get());
367 mCamera->disconnect();
368 }
369
370protected:
371 sp<ProCamera> mCamera;
Igor Murashkin53765732013-02-20 17:41:57 -0800372 sp<ProCameraTestListener> mListener;
373
Igor Murashkin39f79f72013-01-30 10:14:24 -0800374 static sp<Thread> mTestThread;
Igor Murashkin53765732013-02-20 17:41:57 -0800375
Igor Murashkin68506fd2013-02-20 17:57:31 -0800376 int mDisplaySecs;
Igor Murashkindcb07d52013-02-21 14:18:10 -0800377 int mDisplayFmt;
378 int mDisplayW;
379 int mDisplayH;
380
Igor Murashkin68506fd2013-02-20 17:57:31 -0800381 sp<SurfaceComposerClient> mComposerClient;
382 sp<SurfaceControl> mSurfaceControl;
383
Igor Murashkin5835cc42013-02-20 19:29:53 -0800384 sp<SurfaceComposerClient> mDepthComposerClient;
385 sp<SurfaceControl> mDepthSurfaceControl;
386
Igor Murashkin68506fd2013-02-20 17:57:31 -0800387 int getSurfaceWidth() {
388 return 512;
389 }
390 int getSurfaceHeight() {
391 return 512;
392 }
393
394 void createOnScreenSurface(sp<Surface>& surface) {
395 mComposerClient = new SurfaceComposerClient;
396 ASSERT_EQ(NO_ERROR, mComposerClient->initCheck());
397
398 mSurfaceControl = mComposerClient->createSurface(
399 String8("ProCameraTest StreamingImage Surface"),
400 getSurfaceWidth(), getSurfaceHeight(),
401 PIXEL_FORMAT_RGB_888, 0);
402
Igor Murashkindcb07d52013-02-21 14:18:10 -0800403 mSurfaceControl->setPosition(0, 0);
Igor Murashkin5835cc42013-02-20 19:29:53 -0800404
Igor Murashkin68506fd2013-02-20 17:57:31 -0800405 ASSERT_TRUE(mSurfaceControl != NULL);
406 ASSERT_TRUE(mSurfaceControl->isValid());
407
408 SurfaceComposerClient::openGlobalTransaction();
409 ASSERT_EQ(NO_ERROR, mSurfaceControl->setLayer(0x7FFFFFFF));
410 ASSERT_EQ(NO_ERROR, mSurfaceControl->show());
411 SurfaceComposerClient::closeGlobalTransaction();
412
413 sp<ANativeWindow> window = mSurfaceControl->getSurface();
414 surface = mSurfaceControl->getSurface();
415
416 ASSERT_NE((void*)NULL, surface.get());
417 }
418
Igor Murashkin5835cc42013-02-20 19:29:53 -0800419 void createDepthOnScreenSurface(sp<Surface>& surface) {
420 mDepthComposerClient = new SurfaceComposerClient;
421 ASSERT_EQ(NO_ERROR, mDepthComposerClient->initCheck());
422
423 mDepthSurfaceControl = mDepthComposerClient->createSurface(
424 String8("ProCameraTest StreamingImage Surface"),
425 getSurfaceWidth(), getSurfaceHeight(),
426 PIXEL_FORMAT_RGB_888, 0);
427
428 mDepthSurfaceControl->setPosition(640, 0);
429
430 ASSERT_TRUE(mDepthSurfaceControl != NULL);
431 ASSERT_TRUE(mDepthSurfaceControl->isValid());
432
433 SurfaceComposerClient::openGlobalTransaction();
434 ASSERT_EQ(NO_ERROR, mDepthSurfaceControl->setLayer(0x7FFFFFFF));
435 ASSERT_EQ(NO_ERROR, mDepthSurfaceControl->show());
436 SurfaceComposerClient::closeGlobalTransaction();
437
438 sp<ANativeWindow> window = mDepthSurfaceControl->getSurface();
439 surface = mDepthSurfaceControl->getSurface();
440
441 ASSERT_NE((void*)NULL, surface.get());
442 }
443
Igor Murashkin7b33a742013-02-21 13:49:26 -0800444 template <typename T>
Igor Murashkindcb07d52013-02-21 14:18:10 -0800445 static bool ExistsItem(T needle, T* array, size_t count) {
446 if (!array) {
447 return false;
448 }
449
Igor Murashkina140a6e2013-02-21 14:45:03 -0800450 for (size_t i = 0; i < count; ++i) {
Igor Murashkin7b33a742013-02-21 13:49:26 -0800451 if (array[i] == needle) {
452 return true;
453 }
454 }
455 return false;
456 }
457
Igor Murashkindcb07d52013-02-21 14:18:10 -0800458
459 static int FormatFromString(const char* str) {
460 std::string s(str);
461
462#define CMP_STR(x, y) \
463 if (s == #x) return HAL_PIXEL_FORMAT_ ## y;
464#define CMP_STR_SAME(x) CMP_STR(x, x)
465
466 CMP_STR_SAME( Y16);
467 CMP_STR_SAME( Y8);
468 CMP_STR_SAME( YV12);
469 CMP_STR(NV16, YCbCr_422_SP);
470 CMP_STR(NV21, YCrCb_420_SP);
471 CMP_STR(YUY2, YCbCr_422_I);
472 CMP_STR(RAW, RAW_SENSOR);
473 CMP_STR(RGBA, RGBA_8888);
474
475 std::cerr << "Unknown format string " << str << std::endl;
476 return -1;
477
478 }
479
480 /**
481 * Creating a streaming request for these output streams from a template,
482 * and submit it
483 */
Zhijun Hed1d64672013-09-06 15:00:01 -0700484 void createSubmitRequestForStreams(int32_t* streamIds, size_t count, int requestCount=-1) {
Igor Murashkindcb07d52013-02-21 14:18:10 -0800485
486 ASSERT_NE((void*)NULL, streamIds);
Igor Murashkina140a6e2013-02-21 14:45:03 -0800487 ASSERT_LT(0u, count);
Igor Murashkindcb07d52013-02-21 14:18:10 -0800488
489 camera_metadata_t *requestTmp = NULL;
490 EXPECT_OK(mCamera->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
491 /*out*/&requestTmp));
492 ASSERT_NE((void*)NULL, requestTmp);
493 CameraMetadata request(requestTmp);
494
495 // set the output streams. default is empty
496
497 uint32_t tag = static_cast<uint32_t>(ANDROID_REQUEST_OUTPUT_STREAMS);
498 request.update(tag, streamIds, count);
499
500 requestTmp = request.release();
Igor Murashkina140a6e2013-02-21 14:45:03 -0800501
502 if (requestCount < 0) {
503 EXPECT_OK(mCamera->submitRequest(requestTmp, /*streaming*/true));
504 } else {
505 for (int i = 0; i < requestCount; ++i) {
506 EXPECT_OK(mCamera->submitRequest(requestTmp,
507 /*streaming*/false));
508 }
509 }
Igor Murashkindcb07d52013-02-21 14:18:10 -0800510 request.acquire(requestTmp);
511 }
Igor Murashkin634a5152013-02-20 17:15:11 -0800512};
513
Igor Murashkin39f79f72013-01-30 10:14:24 -0800514sp<Thread> ProCameraTest::mTestThread;
515
Igor Murashkin7b33a742013-02-21 13:49:26 -0800516TEST_F(ProCameraTest, AvailableFormats) {
517 if (HasFatalFailure()) {
518 return;
519 }
520
Igor Murashkindcb07d52013-02-21 14:18:10 -0800521 CameraMetadata staticInfo = mCamera->getCameraInfo(CAMERA_ID);
522 ASSERT_FALSE(staticInfo.isEmpty());
Igor Murashkin7b33a742013-02-21 13:49:26 -0800523
Igor Murashkin7b33a742013-02-21 13:49:26 -0800524 uint32_t tag = static_cast<uint32_t>(ANDROID_SCALER_AVAILABLE_FORMATS);
Igor Murashkindcb07d52013-02-21 14:18:10 -0800525 EXPECT_TRUE(staticInfo.exists(tag));
526 camera_metadata_entry_t entry = staticInfo.find(tag);
Igor Murashkin7b33a742013-02-21 13:49:26 -0800527
Igor Murashkindcb07d52013-02-21 14:18:10 -0800528 EXPECT_TRUE(ExistsItem<int32_t>(HAL_PIXEL_FORMAT_YV12,
Igor Murashkin7b33a742013-02-21 13:49:26 -0800529 entry.data.i32, entry.count));
Igor Murashkindcb07d52013-02-21 14:18:10 -0800530 EXPECT_TRUE(ExistsItem<int32_t>(HAL_PIXEL_FORMAT_YCrCb_420_SP,
Igor Murashkin7b33a742013-02-21 13:49:26 -0800531 entry.data.i32, entry.count));
Igor Murashkin7b33a742013-02-21 13:49:26 -0800532}
533
Igor Murashkin39f79f72013-01-30 10:14:24 -0800534// test around exclusiveTryLock (immediate locking)
Igor Murashkin53765732013-02-20 17:41:57 -0800535TEST_F(ProCameraTest, LockingImmediate) {
Igor Murashkin634a5152013-02-20 17:15:11 -0800536
537 if (HasFatalFailure()) {
538 return;
539 }
540
Igor Murashkina91537e2013-02-21 12:02:29 -0800541 mListener->SetEventMask(ProEvent_Mask(ACQUIRED) |
542 ProEvent_Mask(STOLEN) |
543 ProEvent_Mask(RELEASED));
544
Igor Murashkin53765732013-02-20 17:41:57 -0800545 EXPECT_FALSE(mCamera->hasExclusiveLock());
546 EXPECT_EQ(OK, mCamera->exclusiveTryLock());
Igor Murashkin39f79f72013-01-30 10:14:24 -0800547 // at this point we definitely have the lock
548
549 EXPECT_EQ(OK, mListener->WaitForEvent());
550 EXPECT_EQ(ACQUIRED, mListener->ReadEvent());
551
552 EXPECT_TRUE(mCamera->hasExclusiveLock());
553 EXPECT_EQ(OK, mCamera->exclusiveUnlock());
554
555 EXPECT_EQ(OK, mListener->WaitForEvent());
556 EXPECT_EQ(RELEASED, mListener->ReadEvent());
557
558 EXPECT_FALSE(mCamera->hasExclusiveLock());
559}
560
561// test around exclusiveLock (locking at some future point in time)
562TEST_F(ProCameraTest, LockingAsynchronous) {
563
564 if (HasFatalFailure()) {
565 return;
566 }
567
Igor Murashkina91537e2013-02-21 12:02:29 -0800568
569 mListener->SetEventMask(ProEvent_Mask(ACQUIRED) |
570 ProEvent_Mask(STOLEN) |
571 ProEvent_Mask(RELEASED));
572
Igor Murashkin39f79f72013-01-30 10:14:24 -0800573 // TODO: Add another procamera that has a lock here.
574 // then we can be test that the lock wont immediately be acquired
575
576 EXPECT_FALSE(mCamera->hasExclusiveLock());
Igor Murashkina91537e2013-02-21 12:02:29 -0800577 EXPECT_EQ(OK, mCamera->exclusiveTryLock());
578 // at this point we definitely have the lock
Igor Murashkin53765732013-02-20 17:41:57 -0800579
580 EXPECT_EQ(OK, mListener->WaitForEvent());
581 EXPECT_EQ(ACQUIRED, mListener->ReadEvent());
582
583 EXPECT_TRUE(mCamera->hasExclusiveLock());
584 EXPECT_EQ(OK, mCamera->exclusiveUnlock());
585
586 EXPECT_EQ(OK, mListener->WaitForEvent());
587 EXPECT_EQ(RELEASED, mListener->ReadEvent());
588
589 EXPECT_FALSE(mCamera->hasExclusiveLock());
Igor Murashkin634a5152013-02-20 17:15:11 -0800590}
591
Igor Murashkin68506fd2013-02-20 17:57:31 -0800592// Stream directly to the screen.
Igor Murashkina91537e2013-02-21 12:02:29 -0800593TEST_F(ProCameraTest, DISABLED_StreamingImageSingle) {
Igor Murashkin68506fd2013-02-20 17:57:31 -0800594 if (HasFatalFailure()) {
595 return;
596 }
Igor Murashkin68506fd2013-02-20 17:57:31 -0800597
Igor Murashkindcb07d52013-02-21 14:18:10 -0800598 sp<Surface> surface;
Igor Murashkin68506fd2013-02-20 17:57:31 -0800599 if (mDisplaySecs > 0) {
Igor Murashkindcb07d52013-02-21 14:18:10 -0800600 createOnScreenSurface(/*out*/surface);
601 }
602 else {
603 dout << "Skipping, will not render to screen" << std::endl;
604 return;
Igor Murashkin68506fd2013-02-20 17:57:31 -0800605 }
Igor Murashkin5835cc42013-02-20 19:29:53 -0800606
607 int depthStreamId = -1;
Igor Murashkin68506fd2013-02-20 17:57:31 -0800608
Igor Murashkinbfc99152013-02-27 12:55:20 -0800609 sp<ServiceListener> listener = new ServiceListener();
610 EXPECT_OK(ProCamera::addServiceListener(listener));
Igor Murashkin68506fd2013-02-20 17:57:31 -0800611
Igor Murashkincba2c162013-03-20 15:56:31 -0700612 ServiceListener::Status currentStatus;
613
614 // when subscribing a new listener,
615 // we immediately get a callback to the current status
616 while (listener->waitForStatusChange(/*out*/currentStatus) != OK);
617 EXPECT_EQ(ServiceListener::STATUS_PRESENT, currentStatus);
Igor Murashkin68506fd2013-02-20 17:57:31 -0800618
Igor Murashkinbfc99152013-02-27 12:55:20 -0800619 dout << "Will now stream and resume infinitely..." << std::endl;
620 while (true) {
Igor Murashkin68506fd2013-02-20 17:57:31 -0800621
Igor Murashkincba2c162013-03-20 15:56:31 -0700622 if (currentStatus == ServiceListener::STATUS_PRESENT) {
Igor Murashkinbfc99152013-02-27 12:55:20 -0800623
Igor Murashkincba2c162013-03-20 15:56:31 -0700624 ASSERT_OK(mCamera->createStream(mDisplayW, mDisplayH, mDisplayFmt,
Igor Murashkinbfc99152013-02-27 12:55:20 -0800625 surface,
626 &depthStreamId));
627 EXPECT_NE(-1, depthStreamId);
628
629 EXPECT_OK(mCamera->exclusiveTryLock());
630
Zhijun Hed1d64672013-09-06 15:00:01 -0700631 int32_t streams[] = { depthStreamId };
Igor Murashkinbfc99152013-02-27 12:55:20 -0800632 ASSERT_NO_FATAL_FAILURE(createSubmitRequestForStreams(
633 streams,
634 /*count*/1));
635 }
636
637 ServiceListener::Status stat = ServiceListener::STATUS_UNKNOWN;
638
639 // TODO: maybe check for getch every once in a while?
640 while (listener->waitForStatusChange(/*out*/stat) != OK);
641
642 if (currentStatus != stat) {
Igor Murashkincba2c162013-03-20 15:56:31 -0700643 if (stat == ServiceListener::STATUS_PRESENT) {
Igor Murashkinbfc99152013-02-27 12:55:20 -0800644 dout << "Reconnecting to camera" << std::endl;
645 mCamera = ProCamera::connect(CAMERA_ID);
646 } else if (stat == ServiceListener::STATUS_NOT_AVAILABLE) {
647 dout << "Disconnecting from camera" << std::endl;
648 mCamera->disconnect();
Igor Murashkincba2c162013-03-20 15:56:31 -0700649 } else if (stat == ServiceListener::STATUS_NOT_PRESENT) {
650 dout << "Camera unplugged" << std::endl;
651 mCamera = NULL;
Igor Murashkinbfc99152013-02-27 12:55:20 -0800652 } else {
653 dout << "Unknown status change "
654 << std::hex << stat << std::endl;
655 }
656
657 currentStatus = stat;
658 }
659 }
660
661 EXPECT_OK(ProCamera::removeServiceListener(listener));
Igor Murashkindcb07d52013-02-21 14:18:10 -0800662 EXPECT_OK(mCamera->deleteStream(depthStreamId));
Igor Murashkin5835cc42013-02-20 19:29:53 -0800663 EXPECT_OK(mCamera->exclusiveUnlock());
664}
665
Igor Murashkineb72e172013-02-21 11:43:14 -0800666// Stream directly to the screen.
Igor Murashkina91537e2013-02-21 12:02:29 -0800667TEST_F(ProCameraTest, DISABLED_StreamingImageDual) {
Igor Murashkineb72e172013-02-21 11:43:14 -0800668 if (HasFatalFailure()) {
669 return;
670 }
Igor Murashkineb72e172013-02-21 11:43:14 -0800671 sp<Surface> surface;
672 sp<Surface> depthSurface;
673 if (mDisplaySecs > 0) {
674 createOnScreenSurface(/*out*/surface);
675 createDepthOnScreenSurface(/*out*/depthSurface);
676 }
677
678 int streamId = -1;
679 EXPECT_OK(mCamera->createStream(/*width*/1280, /*height*/960,
680 TEST_FORMAT_MAIN, surface, &streamId));
681 EXPECT_NE(-1, streamId);
682
683 int depthStreamId = -1;
684 EXPECT_OK(mCamera->createStream(/*width*/320, /*height*/240,
685 TEST_FORMAT_DEPTH, depthSurface, &depthStreamId));
686 EXPECT_NE(-1, depthStreamId);
687
688 EXPECT_OK(mCamera->exclusiveTryLock());
689 /*
690 */
691 /* iterate in a loop submitting requests every frame.
692 * what kind of requests doesnt really matter, just whatever.
693 */
694
695 // it would probably be better to use CameraMetadata from camera service.
696 camera_metadata_t *request = NULL;
697 EXPECT_OK(mCamera->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
698 /*out*/&request));
699 EXPECT_NE((void*)NULL, request);
700
701 /*FIXME: dont need this later, at which point the above should become an
702 ASSERT_NE*/
703 if(request == NULL) request = allocate_camera_metadata(10, 100);
704
705 // set the output streams to just this stream ID
706
707 // wow what a verbose API.
Zhijun Hed1d64672013-09-06 15:00:01 -0700708 int32_t allStreams[] = { streamId, depthStreamId };
Igor Murashkineb72e172013-02-21 11:43:14 -0800709 // IMPORTANT. bad things will happen if its not a uint8.
710 size_t streamCount = sizeof(allStreams) / sizeof(allStreams[0]);
711 camera_metadata_entry_t entry;
712 uint32_t tag = static_cast<uint32_t>(ANDROID_REQUEST_OUTPUT_STREAMS);
713 int find = find_camera_metadata_entry(request, tag, &entry);
714 if (find == -ENOENT) {
715 if (add_camera_metadata_entry(request, tag, &allStreams,
716 /*data_count*/streamCount) != OK) {
717 camera_metadata_t *tmp = allocate_camera_metadata(1000, 10000);
718 ASSERT_OK(append_camera_metadata(tmp, request));
719 free_camera_metadata(request);
720 request = tmp;
721
722 ASSERT_OK(add_camera_metadata_entry(request, tag, &allStreams,
723 /*data_count*/streamCount));
724 }
725 } else {
726 ASSERT_OK(update_camera_metadata_entry(request, entry.index,
727 &allStreams, /*data_count*/streamCount, &entry));
728 }
729
730 EXPECT_OK(mCamera->submitRequest(request, /*streaming*/true));
731
732 dout << "will sleep now for " << mDisplaySecs << std::endl;
733 sleep(mDisplaySecs);
734
735 free_camera_metadata(request);
736
Zhijun Hed1d64672013-09-06 15:00:01 -0700737 for (size_t i = 0; i < streamCount; ++i) {
Igor Murashkineb72e172013-02-21 11:43:14 -0800738 EXPECT_OK(mCamera->deleteStream(allStreams[i]));
739 }
740 EXPECT_OK(mCamera->exclusiveUnlock());
741}
742
743TEST_F(ProCameraTest, CpuConsumerSingle) {
Igor Murashkin5835cc42013-02-20 19:29:53 -0800744 if (HasFatalFailure()) {
745 return;
746 }
Igor Murashkina91537e2013-02-21 12:02:29 -0800747
Igor Murashkinc6deb682013-04-18 11:53:35 -0700748 mListener->SetEventMask(ProEvent_Mask(ACQUIRED) |
749 ProEvent_Mask(STOLEN) |
750 ProEvent_Mask(RELEASED) |
751 ProEvent_Mask(FRAME_RECEIVED));
752 mListener->SetDropFrames(true);
Igor Murashkina91537e2013-02-21 12:02:29 -0800753
Igor Murashkin5835cc42013-02-20 19:29:53 -0800754 int streamId = -1;
Igor Murashkina140a6e2013-02-21 14:45:03 -0800755 sp<CpuConsumer> consumer;
Igor Murashkin5835cc42013-02-20 19:29:53 -0800756 EXPECT_OK(mCamera->createStreamCpu(/*width*/320, /*height*/240,
Igor Murashkina140a6e2013-02-21 14:45:03 -0800757 TEST_FORMAT_DEPTH, TEST_CPU_HEAP_COUNT, &consumer, &streamId));
Igor Murashkin5835cc42013-02-20 19:29:53 -0800758 EXPECT_NE(-1, streamId);
759
760 EXPECT_OK(mCamera->exclusiveTryLock());
761 EXPECT_EQ(OK, mListener->WaitForEvent());
762 EXPECT_EQ(ACQUIRED, mListener->ReadEvent());
763 /* iterate in a loop submitting requests every frame.
764 * what kind of requests doesnt really matter, just whatever.
765 */
766
767 // it would probably be better to use CameraMetadata from camera service.
768 camera_metadata_t *request = NULL;
769 EXPECT_OK(mCamera->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
770 /*out*/&request));
771 EXPECT_NE((void*)NULL, request);
772
773 /*FIXME: dont need this later, at which point the above should become an
774 ASSERT_NE*/
775 if(request == NULL) request = allocate_camera_metadata(10, 100);
776
777 // set the output streams to just this stream ID
778
Zhijun Hed1d64672013-09-06 15:00:01 -0700779 int32_t allStreams[] = { streamId };
Igor Murashkin5835cc42013-02-20 19:29:53 -0800780 camera_metadata_entry_t entry;
781 uint32_t tag = static_cast<uint32_t>(ANDROID_REQUEST_OUTPUT_STREAMS);
782 int find = find_camera_metadata_entry(request, tag, &entry);
783 if (find == -ENOENT) {
784 if (add_camera_metadata_entry(request, tag, &allStreams,
785 /*data_count*/1) != OK) {
786 camera_metadata_t *tmp = allocate_camera_metadata(1000, 10000);
787 ASSERT_OK(append_camera_metadata(tmp, request));
788 free_camera_metadata(request);
789 request = tmp;
790
791 ASSERT_OK(add_camera_metadata_entry(request, tag, &allStreams,
792 /*data_count*/1));
793 }
794 } else {
795 ASSERT_OK(update_camera_metadata_entry(request, entry.index,
796 &allStreams, /*data_count*/1, &entry));
797 }
798
799 EXPECT_OK(mCamera->submitRequest(request, /*streaming*/true));
800
801 // Consume a couple of frames
802 for (int i = 0; i < TEST_CPU_FRAME_COUNT; ++i) {
803 EXPECT_EQ(OK, mListener->WaitForEvent());
Igor Murashkinc6deb682013-04-18 11:53:35 -0700804 EXPECT_EQ(FRAME_RECEIVED, mListener->ReadEvent());
Igor Murashkin5835cc42013-02-20 19:29:53 -0800805 }
806
807 // Done: clean up
808 free_camera_metadata(request);
809 EXPECT_OK(mCamera->deleteStream(streamId));
Igor Murashkin68506fd2013-02-20 17:57:31 -0800810 EXPECT_OK(mCamera->exclusiveUnlock());
811}
812
Igor Murashkineb72e172013-02-21 11:43:14 -0800813TEST_F(ProCameraTest, CpuConsumerDual) {
814 if (HasFatalFailure()) {
815 return;
816 }
Igor Murashkina91537e2013-02-21 12:02:29 -0800817
Igor Murashkinc6deb682013-04-18 11:53:35 -0700818 mListener->SetEventMask(ProEvent_Mask(FRAME_RECEIVED));
819 mListener->SetDropFrames(true);
Igor Murashkina91537e2013-02-21 12:02:29 -0800820
Igor Murashkineb72e172013-02-21 11:43:14 -0800821 int streamId = -1;
Igor Murashkina140a6e2013-02-21 14:45:03 -0800822 sp<CpuConsumer> consumer;
Igor Murashkineb72e172013-02-21 11:43:14 -0800823 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
Igor Murashkina140a6e2013-02-21 14:45:03 -0800824 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT, &consumer, &streamId));
Igor Murashkineb72e172013-02-21 11:43:14 -0800825 EXPECT_NE(-1, streamId);
826
827 int depthStreamId = -1;
828 EXPECT_OK(mCamera->createStreamCpu(/*width*/320, /*height*/240,
Igor Murashkina140a6e2013-02-21 14:45:03 -0800829 TEST_FORMAT_DEPTH, TEST_CPU_HEAP_COUNT, &consumer, &depthStreamId));
Igor Murashkineb72e172013-02-21 11:43:14 -0800830 EXPECT_NE(-1, depthStreamId);
831
832 EXPECT_OK(mCamera->exclusiveTryLock());
Igor Murashkineb72e172013-02-21 11:43:14 -0800833 /*
834 */
835 /* iterate in a loop submitting requests every frame.
836 * what kind of requests doesnt really matter, just whatever.
837 */
838
839 // it would probably be better to use CameraMetadata from camera service.
840 camera_metadata_t *request = NULL;
841 EXPECT_OK(mCamera->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
842 /*out*/&request));
843 EXPECT_NE((void*)NULL, request);
844
845 if(request == NULL) request = allocate_camera_metadata(10, 100);
846
847 // set the output streams to just this stream ID
848
849 // wow what a verbose API.
Zhijun Hed1d64672013-09-06 15:00:01 -0700850 int32_t allStreams[] = { streamId, depthStreamId };
Igor Murashkineb72e172013-02-21 11:43:14 -0800851 size_t streamCount = 2;
852 camera_metadata_entry_t entry;
853 uint32_t tag = static_cast<uint32_t>(ANDROID_REQUEST_OUTPUT_STREAMS);
854 int find = find_camera_metadata_entry(request, tag, &entry);
855 if (find == -ENOENT) {
856 if (add_camera_metadata_entry(request, tag, &allStreams,
857 /*data_count*/streamCount) != OK) {
858 camera_metadata_t *tmp = allocate_camera_metadata(1000, 10000);
859 ASSERT_OK(append_camera_metadata(tmp, request));
860 free_camera_metadata(request);
861 request = tmp;
862
863 ASSERT_OK(add_camera_metadata_entry(request, tag, &allStreams,
864 /*data_count*/streamCount));
865 }
866 } else {
867 ASSERT_OK(update_camera_metadata_entry(request, entry.index,
868 &allStreams, /*data_count*/streamCount, &entry));
869 }
870
871 EXPECT_OK(mCamera->submitRequest(request, /*streaming*/true));
872
873 // Consume a couple of frames
874 for (int i = 0; i < TEST_CPU_FRAME_COUNT; ++i) {
875 // stream id 1
876 EXPECT_EQ(OK, mListener->WaitForEvent());
Igor Murashkinc6deb682013-04-18 11:53:35 -0700877 EXPECT_EQ(FRAME_RECEIVED, mListener->ReadEvent());
Igor Murashkineb72e172013-02-21 11:43:14 -0800878
879 // stream id 2
880 EXPECT_EQ(OK, mListener->WaitForEvent());
Igor Murashkinc6deb682013-04-18 11:53:35 -0700881 EXPECT_EQ(FRAME_RECEIVED, mListener->ReadEvent());
Igor Murashkineb72e172013-02-21 11:43:14 -0800882
883 //TODO: events should be a struct with some data like the stream id
884 }
885
886 // Done: clean up
887 free_camera_metadata(request);
888 EXPECT_OK(mCamera->deleteStream(streamId));
889 EXPECT_OK(mCamera->exclusiveUnlock());
890}
891
Igor Murashkina91537e2013-02-21 12:02:29 -0800892TEST_F(ProCameraTest, ResultReceiver) {
893 if (HasFatalFailure()) {
894 return;
895 }
896
897 mListener->SetEventMask(ProEvent_Mask(RESULT_RECEIVED));
Igor Murashkinc6deb682013-04-18 11:53:35 -0700898 mListener->SetDropFrames(true);
899 //FIXME: if this is run right after the previous test we get FRAME_RECEIVED
Igor Murashkina91537e2013-02-21 12:02:29 -0800900 // need to filter out events at read time
901
902 int streamId = -1;
Igor Murashkina140a6e2013-02-21 14:45:03 -0800903 sp<CpuConsumer> consumer;
Igor Murashkina91537e2013-02-21 12:02:29 -0800904 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
Igor Murashkina140a6e2013-02-21 14:45:03 -0800905 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT, &consumer, &streamId));
Igor Murashkina91537e2013-02-21 12:02:29 -0800906 EXPECT_NE(-1, streamId);
907
908 EXPECT_OK(mCamera->exclusiveTryLock());
909 /*
910 */
911 /* iterate in a loop submitting requests every frame.
912 * what kind of requests doesnt really matter, just whatever.
913 */
914
915 camera_metadata_t *request = NULL;
916 EXPECT_OK(mCamera->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
917 /*out*/&request));
918 EXPECT_NE((void*)NULL, request);
919
920 /*FIXME*/
921 if(request == NULL) request = allocate_camera_metadata(10, 100);
922
923 // set the output streams to just this stream ID
924
Zhijun Hed1d64672013-09-06 15:00:01 -0700925 int32_t allStreams[] = { streamId };
Igor Murashkina91537e2013-02-21 12:02:29 -0800926 size_t streamCount = 1;
927 camera_metadata_entry_t entry;
928 uint32_t tag = static_cast<uint32_t>(ANDROID_REQUEST_OUTPUT_STREAMS);
929 int find = find_camera_metadata_entry(request, tag, &entry);
930 if (find == -ENOENT) {
931 if (add_camera_metadata_entry(request, tag, &allStreams,
932 /*data_count*/streamCount) != OK) {
933 camera_metadata_t *tmp = allocate_camera_metadata(1000, 10000);
934 ASSERT_OK(append_camera_metadata(tmp, request));
935 free_camera_metadata(request);
936 request = tmp;
937
938 ASSERT_OK(add_camera_metadata_entry(request, tag, &allStreams,
939 /*data_count*/streamCount));
940 }
941 } else {
942 ASSERT_OK(update_camera_metadata_entry(request, entry.index,
943 &allStreams, /*data_count*/streamCount, &entry));
944 }
945
946 EXPECT_OK(mCamera->submitRequest(request, /*streaming*/true));
947
948 // Consume a couple of results
949 for (int i = 0; i < TEST_CPU_FRAME_COUNT; ++i) {
950 EXPECT_EQ(OK, mListener->WaitForEvent());
951 EXPECT_EQ(RESULT_RECEIVED, mListener->ReadEvent());
952 }
953
954 // Done: clean up
955 free_camera_metadata(request);
956 EXPECT_OK(mCamera->deleteStream(streamId));
957 EXPECT_OK(mCamera->exclusiveUnlock());
958}
959
Igor Murashkinc6deb682013-04-18 11:53:35 -0700960// FIXME: This is racy and sometimes fails on waitForFrameMetadata
961TEST_F(ProCameraTest, DISABLED_WaitForResult) {
Igor Murashkina140a6e2013-02-21 14:45:03 -0800962 if (HasFatalFailure()) {
963 return;
964 }
965
Igor Murashkinc6deb682013-04-18 11:53:35 -0700966 mListener->SetDropFrames(true);
967
Igor Murashkina140a6e2013-02-21 14:45:03 -0800968 int streamId = -1;
969 sp<CpuConsumer> consumer;
970 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
971 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT, &consumer, &streamId));
972 EXPECT_NE(-1, streamId);
973
974 EXPECT_OK(mCamera->exclusiveTryLock());
975
Zhijun Hed1d64672013-09-06 15:00:01 -0700976 int32_t streams[] = { streamId };
Igor Murashkina140a6e2013-02-21 14:45:03 -0800977 ASSERT_NO_FATAL_FAILURE(createSubmitRequestForStreams(streams, /*count*/1));
978
979 // Consume a couple of results
980 for (int i = 0; i < TEST_CPU_FRAME_COUNT; ++i) {
981 EXPECT_OK(mCamera->waitForFrameMetadata());
982 CameraMetadata meta = mCamera->consumeFrameMetadata();
983 EXPECT_FALSE(meta.isEmpty());
984 }
985
986 // Done: clean up
Igor Murashkina140a6e2013-02-21 14:45:03 -0800987 EXPECT_OK(mCamera->deleteStream(streamId));
988 EXPECT_OK(mCamera->exclusiveUnlock());
989}
990
991TEST_F(ProCameraTest, WaitForSingleStreamBuffer) {
992 if (HasFatalFailure()) {
993 return;
994 }
995
996 int streamId = -1;
997 sp<CpuConsumer> consumer;
998 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
999 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT, &consumer, &streamId));
1000 EXPECT_NE(-1, streamId);
1001
1002 EXPECT_OK(mCamera->exclusiveTryLock());
1003
Zhijun Hed1d64672013-09-06 15:00:01 -07001004 int32_t streams[] = { streamId };
Igor Murashkina140a6e2013-02-21 14:45:03 -08001005 ASSERT_NO_FATAL_FAILURE(createSubmitRequestForStreams(streams, /*count*/1,
1006 /*requests*/TEST_CPU_FRAME_COUNT));
1007
1008 // Consume a couple of results
1009 for (int i = 0; i < TEST_CPU_FRAME_COUNT; ++i) {
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001010 EXPECT_EQ(1, mCamera->waitForFrameBuffer(streamId));
Igor Murashkina140a6e2013-02-21 14:45:03 -08001011
1012 CpuConsumer::LockedBuffer buf;
1013 EXPECT_OK(consumer->lockNextBuffer(&buf));
1014
1015 dout << "Buffer synchronously received on streamId = " << streamId <<
1016 ", dataPtr = " << (void*)buf.data <<
1017 ", timestamp = " << buf.timestamp << std::endl;
1018
1019 EXPECT_OK(consumer->unlockBuffer(buf));
1020 }
1021
1022 // Done: clean up
1023 EXPECT_OK(mCamera->deleteStream(streamId));
1024 EXPECT_OK(mCamera->exclusiveUnlock());
1025}
1026
Igor Murashkinc6deb682013-04-18 11:53:35 -07001027// FIXME: This is racy and sometimes fails on waitForFrameMetadata
1028TEST_F(ProCameraTest, DISABLED_WaitForDualStreamBuffer) {
Igor Murashkina140a6e2013-02-21 14:45:03 -08001029 if (HasFatalFailure()) {
1030 return;
1031 }
1032
1033 const int REQUEST_COUNT = TEST_CPU_FRAME_COUNT * 10;
1034
1035 // 15 fps
1036 int streamId = -1;
1037 sp<CpuConsumer> consumer;
1038 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
1039 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT, &consumer, &streamId));
1040 EXPECT_NE(-1, streamId);
1041
1042 // 30 fps
1043 int depthStreamId = -1;
1044 sp<CpuConsumer> depthConsumer;
1045 EXPECT_OK(mCamera->createStreamCpu(/*width*/320, /*height*/240,
1046 TEST_FORMAT_DEPTH, TEST_CPU_HEAP_COUNT, &depthConsumer, &depthStreamId));
1047 EXPECT_NE(-1, depthStreamId);
1048
1049 EXPECT_OK(mCamera->exclusiveTryLock());
1050
Zhijun Hed1d64672013-09-06 15:00:01 -07001051 int32_t streams[] = { streamId, depthStreamId };
Igor Murashkina140a6e2013-02-21 14:45:03 -08001052 ASSERT_NO_FATAL_FAILURE(createSubmitRequestForStreams(streams, /*count*/2,
1053 /*requests*/REQUEST_COUNT));
1054
Igor Murashkin47539182013-03-18 11:10:48 -07001055 int depthFrames = 0;
1056 int greyFrames = 0;
1057
Igor Murashkina140a6e2013-02-21 14:45:03 -08001058 // Consume two frames simultaneously. Unsynchronized by timestamps.
1059 for (int i = 0; i < REQUEST_COUNT; ++i) {
1060
Igor Murashkin65d79862013-03-27 11:07:06 -07001061 // Exhaust event queue so it doesn't keep growing
1062 while (mListener->ReadEvent() != UNKNOWN);
1063
Igor Murashkina140a6e2013-02-21 14:45:03 -08001064 // Get the metadata
1065 EXPECT_OK(mCamera->waitForFrameMetadata());
1066 CameraMetadata meta = mCamera->consumeFrameMetadata();
1067 EXPECT_FALSE(meta.isEmpty());
1068
1069 // Get the buffers
1070
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001071 EXPECT_EQ(1, mCamera->waitForFrameBuffer(depthStreamId));
Igor Murashkina140a6e2013-02-21 14:45:03 -08001072
1073 /**
1074 * Guaranteed to be able to consume the depth frame,
1075 * since we waited on it.
1076 */
1077 CpuConsumer::LockedBuffer depthBuffer;
1078 EXPECT_OK(depthConsumer->lockNextBuffer(&depthBuffer));
1079
1080 dout << "Depth Buffer synchronously received on streamId = " <<
1081 streamId <<
1082 ", dataPtr = " << (void*)depthBuffer.data <<
1083 ", timestamp = " << depthBuffer.timestamp << std::endl;
1084
1085 EXPECT_OK(depthConsumer->unlockBuffer(depthBuffer));
1086
Igor Murashkin47539182013-03-18 11:10:48 -07001087 depthFrames++;
1088
Igor Murashkina140a6e2013-02-21 14:45:03 -08001089
1090 /** Consume Greyscale frames if there are any.
1091 * There may not be since it runs at half FPS */
1092 CpuConsumer::LockedBuffer greyBuffer;
1093 while (consumer->lockNextBuffer(&greyBuffer) == OK) {
1094
1095 dout << "GRAY Buffer synchronously received on streamId = " <<
1096 streamId <<
1097 ", dataPtr = " << (void*)greyBuffer.data <<
1098 ", timestamp = " << greyBuffer.timestamp << std::endl;
1099
1100 EXPECT_OK(consumer->unlockBuffer(greyBuffer));
Igor Murashkin47539182013-03-18 11:10:48 -07001101
1102 greyFrames++;
Igor Murashkina140a6e2013-02-21 14:45:03 -08001103 }
1104 }
1105
Igor Murashkin47539182013-03-18 11:10:48 -07001106 dout << "Done, summary: depth frames " << std::dec << depthFrames
1107 << ", grey frames " << std::dec << greyFrames << std::endl;
1108
Igor Murashkina140a6e2013-02-21 14:45:03 -08001109 // Done: clean up
1110 EXPECT_OK(mCamera->deleteStream(streamId));
1111 EXPECT_OK(mCamera->exclusiveUnlock());
1112}
1113
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001114TEST_F(ProCameraTest, WaitForSingleStreamBufferAndDropFramesSync) {
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001115 if (HasFatalFailure()) {
1116 return;
1117 }
Igor Murashkina140a6e2013-02-21 14:45:03 -08001118
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001119 const int NUM_REQUESTS = 20 * TEST_CPU_FRAME_COUNT;
1120
1121 int streamId = -1;
1122 sp<CpuConsumer> consumer;
1123 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001124 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT,
1125 /*synchronousMode*/true, &consumer, &streamId));
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001126 EXPECT_NE(-1, streamId);
1127
1128 EXPECT_OK(mCamera->exclusiveTryLock());
1129
Zhijun Hed1d64672013-09-06 15:00:01 -07001130 int32_t streams[] = { streamId };
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001131 ASSERT_NO_FATAL_FAILURE(createSubmitRequestForStreams(streams, /*count*/1,
1132 /*requests*/NUM_REQUESTS));
1133
1134 // Consume a couple of results
1135 for (int i = 0; i < NUM_REQUESTS; ++i) {
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001136 int numFrames;
1137 EXPECT_TRUE((numFrames = mCamera->waitForFrameBuffer(streamId)) > 0);
1138
1139 // Drop all but the newest framebuffer
1140 EXPECT_EQ(numFrames-1, mCamera->dropFrameBuffer(streamId, numFrames-1));
1141
1142 dout << "Dropped " << (numFrames - 1) << " frames" << std::endl;
1143
1144 // Skip the counter ahead, don't try to consume these frames again
1145 i += numFrames-1;
1146
1147 // "Consume" the buffer
1148 CpuConsumer::LockedBuffer buf;
1149 EXPECT_OK(consumer->lockNextBuffer(&buf));
1150
1151 dout << "Buffer synchronously received on streamId = " << streamId <<
1152 ", dataPtr = " << (void*)buf.data <<
1153 ", timestamp = " << buf.timestamp << std::endl;
1154
Igor Murashkin3fa48912013-02-28 10:41:51 -08001155 // Process at 10fps, stream is at 15fps.
1156 // This means we will definitely fill up the buffer queue with
1157 // extra buffers and need to drop them.
1158 usleep(TEST_FRAME_PROCESSING_DELAY_US);
1159
Igor Murashkin4bc4a382013-02-20 13:36:17 -08001160 EXPECT_OK(consumer->unlockBuffer(buf));
1161 }
1162
1163 // Done: clean up
1164 EXPECT_OK(mCamera->deleteStream(streamId));
1165 EXPECT_OK(mCamera->exclusiveUnlock());
1166}
Igor Murashkina140a6e2013-02-21 14:45:03 -08001167
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001168TEST_F(ProCameraTest, WaitForSingleStreamBufferAndDropFramesAsync) {
1169 if (HasFatalFailure()) {
1170 return;
1171 }
1172
1173 const int NUM_REQUESTS = 20 * TEST_CPU_FRAME_COUNT;
1174
1175 int streamId = -1;
1176 sp<CpuConsumer> consumer;
1177 EXPECT_OK(mCamera->createStreamCpu(/*width*/1280, /*height*/960,
1178 TEST_FORMAT_MAIN, TEST_CPU_HEAP_COUNT,
1179 /*synchronousMode*/false, &consumer, &streamId));
1180 EXPECT_NE(-1, streamId);
1181
1182 EXPECT_OK(mCamera->exclusiveTryLock());
1183
Zhijun Hed1d64672013-09-06 15:00:01 -07001184 int32_t streams[] = { streamId };
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001185 ASSERT_NO_FATAL_FAILURE(createSubmitRequestForStreams(streams, /*count*/1,
1186 /*requests*/NUM_REQUESTS));
1187
Igor Murashkinc6deb682013-04-18 11:53:35 -07001188 uint64_t lastFrameNumber = 0;
1189 int numFrames;
1190
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001191 // Consume a couple of results
Igor Murashkinc6deb682013-04-18 11:53:35 -07001192 int i;
1193 for (i = 0; i < NUM_REQUESTS && lastFrameNumber < NUM_REQUESTS; ++i) {
1194 EXPECT_LT(0, (numFrames = mCamera->waitForFrameBuffer(streamId)));
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001195
1196 dout << "Dropped " << (numFrames - 1) << " frames" << std::endl;
1197
1198 // Skip the counter ahead, don't try to consume these frames again
1199 i += numFrames-1;
1200
1201 // "Consume" the buffer
1202 CpuConsumer::LockedBuffer buf;
Igor Murashkinc6deb682013-04-18 11:53:35 -07001203
1204 EXPECT_EQ(OK, consumer->lockNextBuffer(&buf));
1205
1206 lastFrameNumber = buf.frameNumber;
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001207
1208 dout << "Buffer asynchronously received on streamId = " << streamId <<
1209 ", dataPtr = " << (void*)buf.data <<
Igor Murashkinc6deb682013-04-18 11:53:35 -07001210 ", timestamp = " << buf.timestamp <<
1211 ", framenumber = " << buf.frameNumber << std::endl;
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001212
1213 // Process at 10fps, stream is at 15fps.
1214 // This means we will definitely fill up the buffer queue with
1215 // extra buffers and need to drop them.
1216 usleep(TEST_FRAME_PROCESSING_DELAY_US);
1217
1218 EXPECT_OK(consumer->unlockBuffer(buf));
1219 }
1220
Igor Murashkinc6deb682013-04-18 11:53:35 -07001221 dout << "Done after " << i << " iterations " << std::endl;
1222
Igor Murashkinba5ca4e2013-02-28 11:21:00 -08001223 // Done: clean up
1224 EXPECT_OK(mCamera->deleteStream(streamId));
1225 EXPECT_OK(mCamera->exclusiveUnlock());
1226}
1227
Igor Murashkina140a6e2013-02-21 14:45:03 -08001228
1229
Igor Murashkinbfc99152013-02-27 12:55:20 -08001230//TODO: refactor into separate file
1231TEST_F(ProCameraTest, ServiceListenersSubscribe) {
1232
1233 ASSERT_EQ(4u, sizeof(ServiceListener::Status));
1234
1235 sp<ServiceListener> listener = new ServiceListener();
1236
1237 EXPECT_EQ(BAD_VALUE, ProCamera::removeServiceListener(listener));
1238 EXPECT_OK(ProCamera::addServiceListener(listener));
1239
1240 EXPECT_EQ(ALREADY_EXISTS, ProCamera::addServiceListener(listener));
1241 EXPECT_OK(ProCamera::removeServiceListener(listener));
1242
1243 EXPECT_EQ(BAD_VALUE, ProCamera::removeServiceListener(listener));
1244}
1245
1246//TODO: refactor into separate file
1247TEST_F(ProCameraTest, ServiceListenersFunctional) {
1248
1249 sp<ServiceListener> listener = new ServiceListener();
1250
1251 EXPECT_OK(ProCamera::addServiceListener(listener));
1252
1253 sp<Camera> cam = Camera::connect(CAMERA_ID,
1254 /*clientPackageName*/String16(),
1255 -1);
1256 EXPECT_NE((void*)NULL, cam.get());
1257
1258 ServiceListener::Status stat = ServiceListener::STATUS_UNKNOWN;
1259 EXPECT_OK(listener->waitForStatusChange(/*out*/stat));
1260
1261 EXPECT_EQ(ServiceListener::STATUS_NOT_AVAILABLE, stat);
1262
1263 if (cam.get()) {
1264 cam->disconnect();
1265 }
1266
1267 EXPECT_OK(listener->waitForStatusChange(/*out*/stat));
Igor Murashkincba2c162013-03-20 15:56:31 -07001268 EXPECT_EQ(ServiceListener::STATUS_PRESENT, stat);
Igor Murashkinbfc99152013-02-27 12:55:20 -08001269
1270 EXPECT_OK(ProCamera::removeServiceListener(listener));
1271}
1272
1273
1274
Igor Murashkin634a5152013-02-20 17:15:11 -08001275}
1276}
1277}
1278}