1 /*
2 **
3 ** Copyright (C) 2008, The Android Open Source Project
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 ** http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17
18 #define LOG_TAG "CameraService"
19 //#define LOG_NDEBUG 0
20
21 #include <stdio.h>
22 #include <sys/types.h>
23 #include <pthread.h>
24
25 #include <binder/AppOpsManager.h>
26 #include <binder/IPCThreadState.h>
27 #include <binder/IServiceManager.h>
28 #include <binder/MemoryBase.h>
29 #include <binder/MemoryHeapBase.h>
30 #include <cutils/atomic.h>
31 #include <cutils/properties.h>
32 #include <gui/Surface.h>
33 #include <hardware/hardware.h>
34 #include <media/AudioSystem.h>
35 #include <media/mediaplayer.h>
36 #include <utils/Errors.h>
37 #include <utils/Log.h>
38 #include <utils/String16.h>
39
40 #include "CameraService.h"
41 #include "CameraClient.h"
42 #include "Camera2Client.h"
43 #include "ProCamera2Client.h"
44
45 namespace android {
46
47 // ----------------------------------------------------------------------------
48 // Logging support -- this is for debugging only
49 // Use "adb shell dumpsys media.camera -v 1" to change it.
50 volatile int32_t gLogLevel = 0;
51
52 #define LOG1(...) ALOGD_IF(gLogLevel >= 1, __VA_ARGS__);
53 #define LOG2(...) ALOGD_IF(gLogLevel >= 2, __VA_ARGS__);
54
setLogLevel(int level)55 static void setLogLevel(int level) {
56 android_atomic_write(level, &gLogLevel);
57 }
58
59 // ----------------------------------------------------------------------------
60
getCallingPid()61 static int getCallingPid() {
62 return IPCThreadState::self()->getCallingPid();
63 }
64
getCallingUid()65 static int getCallingUid() {
66 return IPCThreadState::self()->getCallingUid();
67 }
68
69 extern "C" {
camera_device_status_change(const struct camera_module_callbacks * callbacks,int camera_id,int new_status)70 static void camera_device_status_change(
71 const struct camera_module_callbacks* callbacks,
72 int camera_id,
73 int new_status) {
74 sp<CameraService> cs = const_cast<CameraService*>(
75 static_cast<const CameraService*>(callbacks));
76
77 cs->onDeviceStatusChanged(
78 camera_id,
79 new_status);
80 }
81 } // extern "C"
82
83 // ----------------------------------------------------------------------------
84
85 // This is ugly and only safe if we never re-create the CameraService, but
86 // should be ok for now.
87 static CameraService *gCameraService;
88
CameraService()89 CameraService::CameraService()
90 :mSoundRef(0), mModule(0)
91 {
92 ALOGI("CameraService started (pid=%d)", getpid());
93 gCameraService = this;
94
95 for (size_t i = 0; i < MAX_CAMERAS; ++i) {
96 mStatusList[i] = ICameraServiceListener::STATUS_PRESENT;
97 }
98
99 this->camera_device_status_change = android::camera_device_status_change;
100 }
101
onFirstRef()102 void CameraService::onFirstRef()
103 {
104 LOG1("CameraService::onFirstRef");
105
106 BnCameraService::onFirstRef();
107
108 if (hw_get_module(CAMERA_HARDWARE_MODULE_ID,
109 (const hw_module_t **)&mModule) < 0) {
110 ALOGE("Could not load camera HAL module");
111 mNumberOfCameras = 0;
112 }
113 else {
114 ALOGI("Loaded \"%s\" camera module", mModule->common.name);
115 mNumberOfCameras = mModule->get_number_of_cameras();
116 if (mNumberOfCameras > MAX_CAMERAS) {
117 ALOGE("Number of cameras(%d) > MAX_CAMERAS(%d).",
118 mNumberOfCameras, MAX_CAMERAS);
119 mNumberOfCameras = MAX_CAMERAS;
120 }
121 for (int i = 0; i < mNumberOfCameras; i++) {
122 setCameraFree(i);
123 }
124
125 if (mModule->common.module_api_version >=
126 CAMERA_MODULE_API_VERSION_2_1) {
127 mModule->set_callbacks(this);
128 }
129 }
130 }
131
~CameraService()132 CameraService::~CameraService() {
133 for (int i = 0; i < mNumberOfCameras; i++) {
134 if (mBusy[i]) {
135 ALOGE("camera %d is still in use in destructor!", i);
136 }
137 }
138
139 gCameraService = NULL;
140 }
141
onDeviceStatusChanged(int cameraId,int newStatus)142 void CameraService::onDeviceStatusChanged(int cameraId,
143 int newStatus)
144 {
145 ALOGI("%s: Status changed for cameraId=%d, newStatus=%d", __FUNCTION__,
146 cameraId, newStatus);
147
148 if (cameraId < 0 || cameraId >= MAX_CAMERAS) {
149 ALOGE("%s: Bad camera ID %d", __FUNCTION__, cameraId);
150 return;
151 }
152
153 if ((int)getStatus(cameraId) == newStatus) {
154 ALOGE("%s: State transition to the same status 0x%x not allowed",
155 __FUNCTION__, (uint32_t)newStatus);
156 return;
157 }
158
159 /* don't do this in updateStatus
160 since it is also called from connect and we could get into a deadlock */
161 if (newStatus == CAMERA_DEVICE_STATUS_NOT_PRESENT) {
162 Vector<sp<BasicClient> > clientsToDisconnect;
163 {
164 Mutex::Autolock al(mServiceLock);
165
166 /* Find all clients that we need to disconnect */
167 sp<Client> client = mClient[cameraId].promote();
168 if (client.get() != NULL) {
169 clientsToDisconnect.push_back(client);
170 }
171
172 int i = cameraId;
173 for (size_t j = 0; j < mProClientList[i].size(); ++j) {
174 sp<ProClient> cl = mProClientList[i][j].promote();
175 if (cl != NULL) {
176 clientsToDisconnect.push_back(cl);
177 }
178 }
179 }
180
181 /* now disconnect them. don't hold the lock
182 or we can get into a deadlock */
183
184 for (size_t i = 0; i < clientsToDisconnect.size(); ++i) {
185 sp<BasicClient> client = clientsToDisconnect[i];
186
187 client->disconnect();
188 /**
189 * The remote app will no longer be able to call methods on the
190 * client since the client PID will be reset to 0
191 */
192 }
193
194 ALOGV("%s: After unplug, disconnected %d clients",
195 __FUNCTION__, clientsToDisconnect.size());
196 }
197
198 updateStatus(
199 static_cast<ICameraServiceListener::Status>(newStatus), cameraId);
200
201 }
202
getNumberOfCameras()203 int32_t CameraService::getNumberOfCameras() {
204 return mNumberOfCameras;
205 }
206
getCameraInfo(int cameraId,struct CameraInfo * cameraInfo)207 status_t CameraService::getCameraInfo(int cameraId,
208 struct CameraInfo* cameraInfo) {
209 if (!mModule) {
210 return NO_INIT;
211 }
212
213 if (cameraId < 0 || cameraId >= mNumberOfCameras) {
214 return BAD_VALUE;
215 }
216
217 struct camera_info info;
218 status_t rc = mModule->get_camera_info(cameraId, &info);
219 cameraInfo->facing = info.facing;
220 cameraInfo->orientation = info.orientation;
221 return rc;
222 }
223
getDeviceVersion(int cameraId,int * facing)224 int CameraService::getDeviceVersion(int cameraId, int* facing) {
225 struct camera_info info;
226 if (mModule->get_camera_info(cameraId, &info) != OK) {
227 return -1;
228 }
229
230 int deviceVersion;
231 if (mModule->common.module_api_version >= CAMERA_MODULE_API_VERSION_2_0) {
232 deviceVersion = info.device_version;
233 } else {
234 deviceVersion = CAMERA_DEVICE_API_VERSION_1_0;
235 }
236
237 if (facing) {
238 *facing = info.facing;
239 }
240
241 return deviceVersion;
242 }
243
isValidCameraId(int cameraId)244 bool CameraService::isValidCameraId(int cameraId) {
245 int facing;
246 int deviceVersion = getDeviceVersion(cameraId, &facing);
247
248 switch(deviceVersion) {
249 case CAMERA_DEVICE_API_VERSION_1_0:
250 case CAMERA_DEVICE_API_VERSION_2_0:
251 case CAMERA_DEVICE_API_VERSION_2_1:
252 case CAMERA_DEVICE_API_VERSION_3_0:
253 return true;
254 default:
255 return false;
256 }
257
258 return false;
259 }
260
validateConnect(int cameraId,int & clientUid) const261 bool CameraService::validateConnect(int cameraId,
262 /*inout*/
263 int& clientUid) const {
264
265 int callingPid = getCallingPid();
266
267 if (clientUid == USE_CALLING_UID) {
268 clientUid = getCallingUid();
269 } else {
270 // We only trust our own process to forward client UIDs
271 if (callingPid != getpid()) {
272 ALOGE("CameraService::connect X (pid %d) rejected (don't trust clientUid)",
273 callingPid);
274 return false;
275 }
276 }
277
278 if (!mModule) {
279 ALOGE("Camera HAL module not loaded");
280 return false;
281 }
282
283 if (cameraId < 0 || cameraId >= mNumberOfCameras) {
284 ALOGE("CameraService::connect X (pid %d) rejected (invalid cameraId %d).",
285 callingPid, cameraId);
286 return false;
287 }
288
289 char value[PROPERTY_VALUE_MAX];
290 property_get("sys.secpolicy.camera.disabled", value, "0");
291 if (strcmp(value, "1") == 0) {
292 // Camera is disabled by DevicePolicyManager.
293 ALOGI("Camera is disabled. connect X (pid %d) rejected", callingPid);
294 return false;
295 }
296
297 ICameraServiceListener::Status currentStatus = getStatus(cameraId);
298 if (currentStatus == ICameraServiceListener::STATUS_NOT_PRESENT) {
299 ALOGI("Camera is not plugged in,"
300 " connect X (pid %d) rejected", callingPid);
301 return false;
302 } else if (currentStatus == ICameraServiceListener::STATUS_ENUMERATING) {
303 ALOGI("Camera is enumerating,"
304 " connect X (pid %d) rejected", callingPid);
305 return false;
306 }
307 // Else don't check for STATUS_NOT_AVAILABLE.
308 // -- It's done implicitly in canConnectUnsafe /w the mBusy array
309
310 return true;
311 }
312
canConnectUnsafe(int cameraId,const String16 & clientPackageName,const sp<IBinder> & remoteCallback,sp<Client> & client)313 bool CameraService::canConnectUnsafe(int cameraId,
314 const String16& clientPackageName,
315 const sp<IBinder>& remoteCallback,
316 sp<Client> &client) {
317 String8 clientName8(clientPackageName);
318 int callingPid = getCallingPid();
319
320 if (mClient[cameraId] != 0) {
321 client = mClient[cameraId].promote();
322 if (client != 0) {
323 if (remoteCallback == client->getRemoteCallback()->asBinder()) {
324 LOG1("CameraService::connect X (pid %d) (the same client)",
325 callingPid);
326 return true;
327 } else {
328 // TODOSC: need to support 1 regular client,
329 // multiple shared clients here
330 ALOGW("CameraService::connect X (pid %d) rejected"
331 " (existing client).", callingPid);
332 return false;
333 }
334 }
335 mClient[cameraId].clear();
336 }
337
338 /*
339 mBusy is set to false as the last step of the Client destructor,
340 after which it is guaranteed that the Client destructor has finished (
341 including any inherited destructors)
342
343 We only need this for a Client subclasses since we don't allow
344 multiple Clents to be opened concurrently, but multiple BasicClient
345 would be fine
346 */
347 if (mBusy[cameraId]) {
348 ALOGW("CameraService::connect X (pid %d, \"%s\") rejected"
349 " (camera %d is still busy).", callingPid,
350 clientName8.string(), cameraId);
351 return false;
352 }
353
354 return true;
355 }
356
connect(const sp<ICameraClient> & cameraClient,int cameraId,const String16 & clientPackageName,int clientUid)357 sp<ICamera> CameraService::connect(
358 const sp<ICameraClient>& cameraClient,
359 int cameraId,
360 const String16& clientPackageName,
361 int clientUid) {
362
363 String8 clientName8(clientPackageName);
364 int callingPid = getCallingPid();
365
366 LOG1("CameraService::connect E (pid %d \"%s\", id %d)", callingPid,
367 clientName8.string(), cameraId);
368
369 if (!validateConnect(cameraId, /*inout*/clientUid)) {
370 return NULL;
371 }
372
373 sp<Client> client;
374
375 {
376 Mutex::Autolock lock(mServiceLock);
377 if (!canConnectUnsafe(cameraId, clientPackageName,
378 cameraClient->asBinder(),
379 /*out*/client)) {
380 return NULL;
381 } else if (client.get() != NULL) {
382 return client;
383 }
384
385 int facing = -1;
386 int deviceVersion = getDeviceVersion(cameraId, &facing);
387
388 // If there are other non-exclusive users of the camera,
389 // this will tear them down before we can reuse the camera
390 if (isValidCameraId(cameraId)) {
391 // transition from PRESENT -> NOT_AVAILABLE
392 updateStatus(ICameraServiceListener::STATUS_NOT_AVAILABLE,
393 cameraId);
394 }
395
396 switch(deviceVersion) {
397 case CAMERA_DEVICE_API_VERSION_1_0:
398 client = new CameraClient(this, cameraClient,
399 clientPackageName, cameraId,
400 facing, callingPid, clientUid, getpid());
401 break;
402 case CAMERA_DEVICE_API_VERSION_2_0:
403 case CAMERA_DEVICE_API_VERSION_2_1:
404 case CAMERA_DEVICE_API_VERSION_3_0:
405 client = new Camera2Client(this, cameraClient,
406 clientPackageName, cameraId,
407 facing, callingPid, clientUid, getpid(),
408 deviceVersion);
409 break;
410 case -1:
411 ALOGE("Invalid camera id %d", cameraId);
412 return NULL;
413 default:
414 ALOGE("Unknown camera device HAL version: %d", deviceVersion);
415 return NULL;
416 }
417
418 if (!connectFinishUnsafe(client, client->asBinder())) {
419 // this is probably not recoverable.. maybe the client can try again
420 // OK: we can only get here if we were originally in PRESENT state
421 updateStatus(ICameraServiceListener::STATUS_PRESENT, cameraId);
422
423 return NULL;
424 }
425
426 mClient[cameraId] = client;
427 LOG1("CameraService::connect X (id %d, this pid is %d)", cameraId,
428 getpid());
429 }
430 // important: release the mutex here so the client can call back
431 // into the service from its destructor (can be at the end of the call)
432
433 return client;
434 }
435
connectFinishUnsafe(const sp<BasicClient> & client,const sp<IBinder> & clientBinder)436 bool CameraService::connectFinishUnsafe(const sp<BasicClient>& client,
437 const sp<IBinder>& clientBinder) {
438 if (client->initialize(mModule) != OK) {
439 return false;
440 }
441
442 clientBinder->linkToDeath(this);
443
444 return true;
445 }
446
connect(const sp<IProCameraCallbacks> & cameraCb,int cameraId,const String16 & clientPackageName,int clientUid)447 sp<IProCameraUser> CameraService::connect(
448 const sp<IProCameraCallbacks>& cameraCb,
449 int cameraId,
450 const String16& clientPackageName,
451 int clientUid)
452 {
453 String8 clientName8(clientPackageName);
454 int callingPid = getCallingPid();
455
456 LOG1("CameraService::connectPro E (pid %d \"%s\", id %d)", callingPid,
457 clientName8.string(), cameraId);
458
459 if (!validateConnect(cameraId, /*inout*/clientUid)) {
460 return NULL;
461 }
462
463 sp<ProClient> client;
464 {
465 Mutex::Autolock lock(mServiceLock);
466 {
467 sp<Client> client;
468 if (!canConnectUnsafe(cameraId, clientPackageName,
469 cameraCb->asBinder(),
470 /*out*/client)) {
471 return NULL;
472 }
473 }
474
475 int facing = -1;
476 int deviceVersion = getDeviceVersion(cameraId, &facing);
477
478 switch(deviceVersion) {
479 case CAMERA_DEVICE_API_VERSION_1_0:
480 ALOGE("Camera id %d uses HALv1, doesn't support ProCamera",
481 cameraId);
482 return NULL;
483 break;
484 case CAMERA_DEVICE_API_VERSION_2_0:
485 case CAMERA_DEVICE_API_VERSION_2_1:
486 client = new ProCamera2Client(this, cameraCb, String16(),
487 cameraId, facing, callingPid, USE_CALLING_UID, getpid());
488 break;
489 case -1:
490 ALOGE("Invalid camera id %d", cameraId);
491 return NULL;
492 default:
493 ALOGE("Unknown camera device HAL version: %d", deviceVersion);
494 return NULL;
495 }
496
497 if (!connectFinishUnsafe(client, client->asBinder())) {
498 return NULL;
499 }
500
501 mProClientList[cameraId].push(client);
502
503 LOG1("CameraService::connectPro X (id %d, this pid is %d)", cameraId,
504 getpid());
505 }
506 // important: release the mutex here so the client can call back
507 // into the service from its destructor (can be at the end of the call)
508
509 return client;
510 }
511
addListener(const sp<ICameraServiceListener> & listener)512 status_t CameraService::addListener(
513 const sp<ICameraServiceListener>& listener) {
514 ALOGV("%s: Add listener %p", __FUNCTION__, listener.get());
515
516 Mutex::Autolock lock(mServiceLock);
517
518 Vector<sp<ICameraServiceListener> >::iterator it, end;
519 for (it = mListenerList.begin(); it != mListenerList.end(); ++it) {
520 if ((*it)->asBinder() == listener->asBinder()) {
521 ALOGW("%s: Tried to add listener %p which was already subscribed",
522 __FUNCTION__, listener.get());
523 return ALREADY_EXISTS;
524 }
525 }
526
527 mListenerList.push_back(listener);
528
529 /* Immediately signal current status to this listener only */
530 {
531 Mutex::Autolock m(mStatusMutex) ;
532 int numCams = getNumberOfCameras();
533 for (int i = 0; i < numCams; ++i) {
534 listener->onStatusChanged(mStatusList[i], i);
535 }
536 }
537
538 return OK;
539 }
removeListener(const sp<ICameraServiceListener> & listener)540 status_t CameraService::removeListener(
541 const sp<ICameraServiceListener>& listener) {
542 ALOGV("%s: Remove listener %p", __FUNCTION__, listener.get());
543
544 Mutex::Autolock lock(mServiceLock);
545
546 Vector<sp<ICameraServiceListener> >::iterator it;
547 for (it = mListenerList.begin(); it != mListenerList.end(); ++it) {
548 if ((*it)->asBinder() == listener->asBinder()) {
549 mListenerList.erase(it);
550 return OK;
551 }
552 }
553
554 ALOGW("%s: Tried to remove a listener %p which was not subscribed",
555 __FUNCTION__, listener.get());
556
557 return BAD_VALUE;
558 }
559
removeClientByRemote(const wp<IBinder> & remoteBinder)560 void CameraService::removeClientByRemote(const wp<IBinder>& remoteBinder) {
561 int callingPid = getCallingPid();
562 LOG1("CameraService::removeClientByRemote E (pid %d)", callingPid);
563
564 // Declare this before the lock to make absolutely sure the
565 // destructor won't be called with the lock held.
566 Mutex::Autolock lock(mServiceLock);
567
568 int outIndex;
569 sp<Client> client = findClientUnsafe(remoteBinder, outIndex);
570
571 if (client != 0) {
572 // Found our camera, clear and leave.
573 LOG1("removeClient: clear camera %d", outIndex);
574 mClient[outIndex].clear();
575
576 client->unlinkToDeath(this);
577 } else {
578
579 sp<ProClient> clientPro = findProClientUnsafe(remoteBinder);
580
581 if (clientPro != NULL) {
582 // Found our camera, clear and leave.
583 LOG1("removeClient: clear pro %p", clientPro.get());
584
585 clientPro->getRemoteCallback()->asBinder()->unlinkToDeath(this);
586 }
587 }
588
589 LOG1("CameraService::removeClientByRemote X (pid %d)", callingPid);
590 }
591
findProClientUnsafe(const wp<IBinder> & cameraCallbacksRemote)592 sp<CameraService::ProClient> CameraService::findProClientUnsafe(
593 const wp<IBinder>& cameraCallbacksRemote)
594 {
595 sp<ProClient> clientPro;
596
597 for (int i = 0; i < mNumberOfCameras; ++i) {
598 Vector<size_t> removeIdx;
599
600 for (size_t j = 0; j < mProClientList[i].size(); ++j) {
601 wp<ProClient> cl = mProClientList[i][j];
602
603 sp<ProClient> clStrong = cl.promote();
604 if (clStrong != NULL && clStrong->getRemote() == cameraCallbacksRemote) {
605 clientPro = clStrong;
606 break;
607 } else if (clStrong == NULL) {
608 // mark to clean up dead ptr
609 removeIdx.push(j);
610 }
611 }
612
613 // remove stale ptrs (in reverse so the indices dont change)
614 for (ssize_t j = (ssize_t)removeIdx.size() - 1; j >= 0; --j) {
615 mProClientList[i].removeAt(removeIdx[j]);
616 }
617
618 }
619
620 return clientPro;
621 }
622
findClientUnsafe(const wp<IBinder> & cameraClient,int & outIndex)623 sp<CameraService::Client> CameraService::findClientUnsafe(
624 const wp<IBinder>& cameraClient, int& outIndex) {
625 sp<Client> client;
626
627 for (int i = 0; i < mNumberOfCameras; i++) {
628
629 // This happens when we have already disconnected (or this is
630 // just another unused camera).
631 if (mClient[i] == 0) continue;
632
633 // Promote mClient. It can fail if we are called from this path:
634 // Client::~Client() -> disconnect() -> removeClientByRemote().
635 client = mClient[i].promote();
636
637 // Clean up stale client entry
638 if (client == NULL) {
639 mClient[i].clear();
640 continue;
641 }
642
643 if (cameraClient == client->getRemoteCallback()->asBinder()) {
644 // Found our camera
645 outIndex = i;
646 return client;
647 }
648 }
649
650 outIndex = -1;
651 return NULL;
652 }
653
getClientByIdUnsafe(int cameraId)654 CameraService::Client* CameraService::getClientByIdUnsafe(int cameraId) {
655 if (cameraId < 0 || cameraId >= mNumberOfCameras) return NULL;
656 return mClient[cameraId].unsafe_get();
657 }
658
getClientLockById(int cameraId)659 Mutex* CameraService::getClientLockById(int cameraId) {
660 if (cameraId < 0 || cameraId >= mNumberOfCameras) return NULL;
661 return &mClientLock[cameraId];
662 }
663
getClientByRemote(const wp<IBinder> & cameraClient)664 sp<CameraService::BasicClient> CameraService::getClientByRemote(
665 const wp<IBinder>& cameraClient) {
666
667 // Declare this before the lock to make absolutely sure the
668 // destructor won't be called with the lock held.
669 sp<BasicClient> client;
670
671 Mutex::Autolock lock(mServiceLock);
672
673 int outIndex;
674 client = findClientUnsafe(cameraClient, outIndex);
675
676 return client;
677 }
678
onTransact(uint32_t code,const Parcel & data,Parcel * reply,uint32_t flags)679 status_t CameraService::onTransact(
680 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags) {
681 // Permission checks
682 switch (code) {
683 case BnCameraService::CONNECT:
684 case BnCameraService::CONNECT_PRO:
685 const int pid = getCallingPid();
686 const int self_pid = getpid();
687 if (pid != self_pid) {
688 // we're called from a different process, do the real check
689 if (!checkCallingPermission(
690 String16("android.permission.CAMERA"))) {
691 const int uid = getCallingUid();
692 ALOGE("Permission Denial: "
693 "can't use the camera pid=%d, uid=%d", pid, uid);
694 return PERMISSION_DENIED;
695 }
696 }
697 break;
698 }
699
700 return BnCameraService::onTransact(code, data, reply, flags);
701 }
702
703 // The reason we need this busy bit is a new CameraService::connect() request
704 // may come in while the previous Client's destructor has not been run or is
705 // still running. If the last strong reference of the previous Client is gone
706 // but the destructor has not been finished, we should not allow the new Client
707 // to be created because we need to wait for the previous Client to tear down
708 // the hardware first.
setCameraBusy(int cameraId)709 void CameraService::setCameraBusy(int cameraId) {
710 android_atomic_write(1, &mBusy[cameraId]);
711
712 ALOGV("setCameraBusy cameraId=%d", cameraId);
713 }
714
setCameraFree(int cameraId)715 void CameraService::setCameraFree(int cameraId) {
716 android_atomic_write(0, &mBusy[cameraId]);
717
718 ALOGV("setCameraFree cameraId=%d", cameraId);
719 }
720
721 // We share the media players for shutter and recording sound for all clients.
722 // A reference count is kept to determine when we will actually release the
723 // media players.
724
newMediaPlayer(const char * file)725 MediaPlayer* CameraService::newMediaPlayer(const char *file) {
726 MediaPlayer* mp = new MediaPlayer();
727 if (mp->setDataSource(file, NULL) == NO_ERROR) {
728 mp->setAudioStreamType(AUDIO_STREAM_ENFORCED_AUDIBLE);
729 mp->prepare();
730 } else {
731 ALOGE("Failed to load CameraService sounds: %s", file);
732 return NULL;
733 }
734 return mp;
735 }
736
loadSound()737 void CameraService::loadSound() {
738 Mutex::Autolock lock(mSoundLock);
739 LOG1("CameraService::loadSound ref=%d", mSoundRef);
740 if (mSoundRef++) return;
741
742 mSoundPlayer[SOUND_SHUTTER] = newMediaPlayer("/system/media/audio/ui/camera_click.ogg");
743 mSoundPlayer[SOUND_RECORDING] = newMediaPlayer("/system/media/audio/ui/VideoRecord.ogg");
744 }
745
releaseSound()746 void CameraService::releaseSound() {
747 Mutex::Autolock lock(mSoundLock);
748 LOG1("CameraService::releaseSound ref=%d", mSoundRef);
749 if (--mSoundRef) return;
750
751 for (int i = 0; i < NUM_SOUNDS; i++) {
752 if (mSoundPlayer[i] != 0) {
753 mSoundPlayer[i]->disconnect();
754 mSoundPlayer[i].clear();
755 }
756 }
757 }
758
playSound(sound_kind kind)759 void CameraService::playSound(sound_kind kind) {
760 LOG1("playSound(%d)", kind);
761 Mutex::Autolock lock(mSoundLock);
762 sp<MediaPlayer> player = mSoundPlayer[kind];
763 if (player != 0) {
764 player->seekTo(0);
765 player->start();
766 }
767 }
768
769 // ----------------------------------------------------------------------------
770
Client(const sp<CameraService> & cameraService,const sp<ICameraClient> & cameraClient,const String16 & clientPackageName,int cameraId,int cameraFacing,int clientPid,uid_t clientUid,int servicePid)771 CameraService::Client::Client(const sp<CameraService>& cameraService,
772 const sp<ICameraClient>& cameraClient,
773 const String16& clientPackageName,
774 int cameraId, int cameraFacing,
775 int clientPid, uid_t clientUid,
776 int servicePid) :
777 CameraService::BasicClient(cameraService, cameraClient->asBinder(),
778 clientPackageName,
779 cameraId, cameraFacing,
780 clientPid, clientUid,
781 servicePid)
782 {
783 int callingPid = getCallingPid();
784 LOG1("Client::Client E (pid %d, id %d)", callingPid, cameraId);
785
786 mRemoteCallback = cameraClient;
787
788 cameraService->setCameraBusy(cameraId);
789 cameraService->loadSound();
790
791 LOG1("Client::Client X (pid %d, id %d)", callingPid, cameraId);
792 }
793
794 // tear down the client
~Client()795 CameraService::Client::~Client() {
796 ALOGV("~Client");
797 mDestructionStarted = true;
798
799 mCameraService->releaseSound();
800 // unconditionally disconnect. function is idempotent
801 Client::disconnect();
802 }
803
BasicClient(const sp<CameraService> & cameraService,const sp<IBinder> & remoteCallback,const String16 & clientPackageName,int cameraId,int cameraFacing,int clientPid,uid_t clientUid,int servicePid)804 CameraService::BasicClient::BasicClient(const sp<CameraService>& cameraService,
805 const sp<IBinder>& remoteCallback,
806 const String16& clientPackageName,
807 int cameraId, int cameraFacing,
808 int clientPid, uid_t clientUid,
809 int servicePid):
810 mClientPackageName(clientPackageName)
811 {
812 mCameraService = cameraService;
813 mRemoteBinder = remoteCallback;
814 mCameraId = cameraId;
815 mCameraFacing = cameraFacing;
816 mClientPid = clientPid;
817 mClientUid = clientUid;
818 mServicePid = servicePid;
819 mOpsActive = false;
820 mDestructionStarted = false;
821 }
822
~BasicClient()823 CameraService::BasicClient::~BasicClient() {
824 ALOGV("~BasicClient");
825 mDestructionStarted = true;
826 }
827
disconnect()828 void CameraService::BasicClient::disconnect() {
829 ALOGV("BasicClient::disconnect");
830 mCameraService->removeClientByRemote(mRemoteBinder);
831 // client shouldn't be able to call into us anymore
832 mClientPid = 0;
833 }
834
startCameraOps()835 status_t CameraService::BasicClient::startCameraOps() {
836 int32_t res;
837
838 mOpsCallback = new OpsCallback(this);
839
840 {
841 ALOGV("%s: Start camera ops, package name = %s, client UID = %d",
842 __FUNCTION__, String8(mClientPackageName).string(), mClientUid);
843 }
844
845 mAppOpsManager.startWatchingMode(AppOpsManager::OP_CAMERA,
846 mClientPackageName, mOpsCallback);
847 res = mAppOpsManager.startOp(AppOpsManager::OP_CAMERA,
848 mClientUid, mClientPackageName);
849
850 if (res != AppOpsManager::MODE_ALLOWED) {
851 ALOGI("Camera %d: Access for \"%s\" has been revoked",
852 mCameraId, String8(mClientPackageName).string());
853 return PERMISSION_DENIED;
854 }
855 mOpsActive = true;
856 return OK;
857 }
858
finishCameraOps()859 status_t CameraService::BasicClient::finishCameraOps() {
860 if (mOpsActive) {
861 mAppOpsManager.finishOp(AppOpsManager::OP_CAMERA, mClientUid,
862 mClientPackageName);
863 mOpsActive = false;
864 }
865 mAppOpsManager.stopWatchingMode(mOpsCallback);
866 mOpsCallback.clear();
867
868 return OK;
869 }
870
opChanged(int32_t op,const String16 & packageName)871 void CameraService::BasicClient::opChanged(int32_t op, const String16& packageName) {
872 String8 name(packageName);
873 String8 myName(mClientPackageName);
874
875 if (op != AppOpsManager::OP_CAMERA) {
876 ALOGW("Unexpected app ops notification received: %d", op);
877 return;
878 }
879
880 int32_t res;
881 res = mAppOpsManager.checkOp(AppOpsManager::OP_CAMERA,
882 mClientUid, mClientPackageName);
883 ALOGV("checkOp returns: %d, %s ", res,
884 res == AppOpsManager::MODE_ALLOWED ? "ALLOWED" :
885 res == AppOpsManager::MODE_IGNORED ? "IGNORED" :
886 res == AppOpsManager::MODE_ERRORED ? "ERRORED" :
887 "UNKNOWN");
888
889 if (res != AppOpsManager::MODE_ALLOWED) {
890 ALOGI("Camera %d: Access for \"%s\" revoked", mCameraId,
891 myName.string());
892 // Reset the client PID to allow server-initiated disconnect,
893 // and to prevent further calls by client.
894 mClientPid = getCallingPid();
895 notifyError();
896 disconnect();
897 }
898 }
899
900 // ----------------------------------------------------------------------------
901
getClientLockFromCookie(void * user)902 Mutex* CameraService::Client::getClientLockFromCookie(void* user) {
903 return gCameraService->getClientLockById((int) user);
904 }
905
906 // Provide client pointer for callbacks. Client lock returned from getClientLockFromCookie should
907 // be acquired for this to be safe
getClientFromCookie(void * user)908 CameraService::Client* CameraService::Client::getClientFromCookie(void* user) {
909 Client* client = gCameraService->getClientByIdUnsafe((int) user);
910
911 // This could happen if the Client is in the process of shutting down (the
912 // last strong reference is gone, but the destructor hasn't finished
913 // stopping the hardware).
914 if (client == NULL) return NULL;
915
916 // destruction already started, so should not be accessed
917 if (client->mDestructionStarted) return NULL;
918
919 return client;
920 }
921
notifyError()922 void CameraService::Client::notifyError() {
923 mRemoteCallback->notifyCallback(CAMERA_MSG_ERROR, CAMERA_ERROR_RELEASED, 0);
924 }
925
926 // NOTE: function is idempotent
disconnect()927 void CameraService::Client::disconnect() {
928 ALOGV("Client::disconnect");
929 BasicClient::disconnect();
930 mCameraService->setCameraFree(mCameraId);
931
932 StatusVector rejectSourceStates;
933 rejectSourceStates.push_back(ICameraServiceListener::STATUS_NOT_PRESENT);
934 rejectSourceStates.push_back(ICameraServiceListener::STATUS_ENUMERATING);
935
936 // Transition to PRESENT if the camera is not in either of above 2 states
937 mCameraService->updateStatus(ICameraServiceListener::STATUS_PRESENT,
938 mCameraId,
939 &rejectSourceStates);
940 }
941
OpsCallback(wp<BasicClient> client)942 CameraService::Client::OpsCallback::OpsCallback(wp<BasicClient> client):
943 mClient(client) {
944 }
945
opChanged(int32_t op,const String16 & packageName)946 void CameraService::Client::OpsCallback::opChanged(int32_t op,
947 const String16& packageName) {
948 sp<BasicClient> client = mClient.promote();
949 if (client != NULL) {
950 client->opChanged(op, packageName);
951 }
952 }
953
954 // ----------------------------------------------------------------------------
955 // IProCamera
956 // ----------------------------------------------------------------------------
957
ProClient(const sp<CameraService> & cameraService,const sp<IProCameraCallbacks> & remoteCallback,const String16 & clientPackageName,int cameraId,int cameraFacing,int clientPid,uid_t clientUid,int servicePid)958 CameraService::ProClient::ProClient(const sp<CameraService>& cameraService,
959 const sp<IProCameraCallbacks>& remoteCallback,
960 const String16& clientPackageName,
961 int cameraId,
962 int cameraFacing,
963 int clientPid,
964 uid_t clientUid,
965 int servicePid)
966 : CameraService::BasicClient(cameraService, remoteCallback->asBinder(),
967 clientPackageName, cameraId, cameraFacing,
968 clientPid, clientUid, servicePid)
969 {
970 mRemoteCallback = remoteCallback;
971 }
972
~ProClient()973 CameraService::ProClient::~ProClient() {
974 }
975
notifyError()976 void CameraService::ProClient::notifyError() {
977 mRemoteCallback->notifyCallback(CAMERA_MSG_ERROR, CAMERA_ERROR_RELEASED, 0);
978 }
979
980 // ----------------------------------------------------------------------------
981
982 static const int kDumpLockRetries = 50;
983 static const int kDumpLockSleep = 60000;
984
tryLock(Mutex & mutex)985 static bool tryLock(Mutex& mutex)
986 {
987 bool locked = false;
988 for (int i = 0; i < kDumpLockRetries; ++i) {
989 if (mutex.tryLock() == NO_ERROR) {
990 locked = true;
991 break;
992 }
993 usleep(kDumpLockSleep);
994 }
995 return locked;
996 }
997
dump(int fd,const Vector<String16> & args)998 status_t CameraService::dump(int fd, const Vector<String16>& args) {
999 String8 result;
1000 if (checkCallingPermission(String16("android.permission.DUMP")) == false) {
1001 result.appendFormat("Permission Denial: "
1002 "can't dump CameraService from pid=%d, uid=%d\n",
1003 getCallingPid(),
1004 getCallingUid());
1005 write(fd, result.string(), result.size());
1006 } else {
1007 bool locked = tryLock(mServiceLock);
1008 // failed to lock - CameraService is probably deadlocked
1009 if (!locked) {
1010 result.append("CameraService may be deadlocked\n");
1011 write(fd, result.string(), result.size());
1012 }
1013
1014 bool hasClient = false;
1015 if (!mModule) {
1016 result = String8::format("No camera module available!\n");
1017 write(fd, result.string(), result.size());
1018 return NO_ERROR;
1019 }
1020
1021 result = String8::format("Camera module HAL API version: 0x%x\n",
1022 mModule->common.hal_api_version);
1023 result.appendFormat("Camera module API version: 0x%x\n",
1024 mModule->common.module_api_version);
1025 result.appendFormat("Camera module name: %s\n",
1026 mModule->common.name);
1027 result.appendFormat("Camera module author: %s\n",
1028 mModule->common.author);
1029 result.appendFormat("Number of camera devices: %d\n\n", mNumberOfCameras);
1030 write(fd, result.string(), result.size());
1031 for (int i = 0; i < mNumberOfCameras; i++) {
1032 result = String8::format("Camera %d static information:\n", i);
1033 camera_info info;
1034
1035 status_t rc = mModule->get_camera_info(i, &info);
1036 if (rc != OK) {
1037 result.appendFormat(" Error reading static information!\n");
1038 write(fd, result.string(), result.size());
1039 } else {
1040 result.appendFormat(" Facing: %s\n",
1041 info.facing == CAMERA_FACING_BACK ? "BACK" : "FRONT");
1042 result.appendFormat(" Orientation: %d\n", info.orientation);
1043 int deviceVersion;
1044 if (mModule->common.module_api_version <
1045 CAMERA_MODULE_API_VERSION_2_0) {
1046 deviceVersion = CAMERA_DEVICE_API_VERSION_1_0;
1047 } else {
1048 deviceVersion = info.device_version;
1049 }
1050 result.appendFormat(" Device version: 0x%x\n", deviceVersion);
1051 if (deviceVersion >= CAMERA_DEVICE_API_VERSION_2_0) {
1052 result.appendFormat(" Device static metadata:\n");
1053 write(fd, result.string(), result.size());
1054 dump_indented_camera_metadata(info.static_camera_characteristics,
1055 fd, 2, 4);
1056 } else {
1057 write(fd, result.string(), result.size());
1058 }
1059 }
1060
1061 sp<Client> client = mClient[i].promote();
1062 if (client == 0) {
1063 result = String8::format(" Device is closed, no client instance\n");
1064 write(fd, result.string(), result.size());
1065 continue;
1066 }
1067 hasClient = true;
1068 result = String8::format(" Device is open. Client instance dump:\n");
1069 write(fd, result.string(), result.size());
1070 client->dump(fd, args);
1071 }
1072 if (!hasClient) {
1073 result = String8::format("\nNo active camera clients yet.\n");
1074 write(fd, result.string(), result.size());
1075 }
1076
1077 if (locked) mServiceLock.unlock();
1078
1079 // change logging level
1080 int n = args.size();
1081 for (int i = 0; i + 1 < n; i++) {
1082 String16 verboseOption("-v");
1083 if (args[i] == verboseOption) {
1084 String8 levelStr(args[i+1]);
1085 int level = atoi(levelStr.string());
1086 result = String8::format("\nSetting log level to %d.\n", level);
1087 setLogLevel(level);
1088 write(fd, result.string(), result.size());
1089 }
1090 }
1091
1092 }
1093 return NO_ERROR;
1094 }
1095
binderDied(const wp<IBinder> & who)1096 /*virtual*/void CameraService::binderDied(
1097 const wp<IBinder> &who) {
1098
1099 /**
1100 * While tempting to promote the wp<IBinder> into a sp,
1101 * it's actually not supported by the binder driver
1102 */
1103
1104 ALOGV("java clients' binder died");
1105
1106 sp<BasicClient> cameraClient = getClientByRemote(who);
1107
1108 if (cameraClient == 0) {
1109 ALOGV("java clients' binder death already cleaned up (normal case)");
1110 return;
1111 }
1112
1113 ALOGW("Disconnecting camera client %p since the binder for it "
1114 "died (this pid %d)", cameraClient.get(), getCallingPid());
1115
1116 cameraClient->disconnect();
1117
1118 }
1119
updateStatus(ICameraServiceListener::Status status,int32_t cameraId,const StatusVector * rejectSourceStates)1120 void CameraService::updateStatus(ICameraServiceListener::Status status,
1121 int32_t cameraId,
1122 const StatusVector *rejectSourceStates) {
1123 // do not lock mServiceLock here or can get into a deadlock from
1124 // connect() -> ProClient::disconnect -> updateStatus
1125 Mutex::Autolock lock(mStatusMutex);
1126
1127 ICameraServiceListener::Status oldStatus = mStatusList[cameraId];
1128
1129 mStatusList[cameraId] = status;
1130
1131 if (oldStatus != status) {
1132 ALOGV("%s: Status has changed for camera ID %d from 0x%x to 0x%x",
1133 __FUNCTION__, cameraId, (uint32_t)oldStatus, (uint32_t)status);
1134
1135 if (oldStatus == ICameraServiceListener::STATUS_NOT_PRESENT &&
1136 (status != ICameraServiceListener::STATUS_PRESENT &&
1137 status != ICameraServiceListener::STATUS_ENUMERATING)) {
1138
1139 ALOGW("%s: From NOT_PRESENT can only transition into PRESENT"
1140 " or ENUMERATING", __FUNCTION__);
1141 mStatusList[cameraId] = oldStatus;
1142 return;
1143 }
1144
1145 if (rejectSourceStates != NULL) {
1146 const StatusVector &rejectList = *rejectSourceStates;
1147 StatusVector::const_iterator it = rejectList.begin();
1148
1149 /**
1150 * Sometimes we want to conditionally do a transition.
1151 * For example if a client disconnects, we want to go to PRESENT
1152 * only if we weren't already in NOT_PRESENT or ENUMERATING.
1153 */
1154 for (; it != rejectList.end(); ++it) {
1155 if (oldStatus == *it) {
1156 ALOGV("%s: Rejecting status transition for Camera ID %d, "
1157 " since the source state was was in one of the bad "
1158 " states.", __FUNCTION__, cameraId);
1159 mStatusList[cameraId] = oldStatus;
1160 return;
1161 }
1162 }
1163 }
1164
1165 /**
1166 * ProClients lose their exclusive lock.
1167 * - Done before the CameraClient can initialize the HAL device,
1168 * since we want to be able to close it before they get to initialize
1169 */
1170 if (status == ICameraServiceListener::STATUS_NOT_AVAILABLE) {
1171 Vector<wp<ProClient> > proClients(mProClientList[cameraId]);
1172 Vector<wp<ProClient> >::const_iterator it;
1173
1174 for (it = proClients.begin(); it != proClients.end(); ++it) {
1175 sp<ProClient> proCl = it->promote();
1176 if (proCl.get() != NULL) {
1177 proCl->onExclusiveLockStolen();
1178 }
1179 }
1180 }
1181
1182 Vector<sp<ICameraServiceListener> >::const_iterator it;
1183 for (it = mListenerList.begin(); it != mListenerList.end(); ++it) {
1184 (*it)->onStatusChanged(status, cameraId);
1185 }
1186 }
1187 }
1188
getStatus(int cameraId) const1189 ICameraServiceListener::Status CameraService::getStatus(int cameraId) const {
1190 if (cameraId < 0 || cameraId >= MAX_CAMERAS) {
1191 ALOGE("%s: Invalid camera ID %d", __FUNCTION__, cameraId);
1192 return ICameraServiceListener::STATUS_UNKNOWN;
1193 }
1194
1195 Mutex::Autolock al(mStatusMutex);
1196 return mStatusList[cameraId];
1197 }
1198
1199 }; // namespace android
1200