blob: b86651fadf67b98cb4ea7506eb87e82bbb635a6c [file] [log] [blame]
Mathias Agopian3cf61352010-02-09 17:46:37 -08001/*
2**
3** Copyright 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
Igor Murashkinbef3f232013-05-30 17:47:38 -070018#define LOG_TAG "BpCameraService"
19#include <utils/Log.h>
Ruben Brunkd1176ef2014-02-21 10:51:38 -080020#include <utils/Errors.h>
Igor Murashkinbef3f232013-05-30 17:47:38 -070021
Mathias Agopian3cf61352010-02-09 17:46:37 -080022#include <stdint.h>
23#include <sys/types.h>
24
25#include <binder/Parcel.h>
26#include <binder/IPCThreadState.h>
27#include <binder/IServiceManager.h>
28
29#include <camera/ICameraService.h>
Igor Murashkinbfc99152013-02-27 12:55:20 -080030#include <camera/ICameraServiceListener.h>
Igor Murashkinc073ba52013-02-26 14:32:34 -080031#include <camera/IProCameraUser.h>
32#include <camera/IProCameraCallbacks.h>
33#include <camera/ICamera.h>
34#include <camera/ICameraClient.h>
Eino-Ville Talvala7b82efe2013-07-25 17:12:35 -070035#include <camera/camera2/ICameraDeviceUser.h>
36#include <camera/camera2/ICameraDeviceCallbacks.h>
Zhijun He2b59be82013-09-25 10:14:30 -070037#include <camera/CameraMetadata.h>
Ruben Brunkd1176ef2014-02-21 10:51:38 -080038#include <camera/VendorTagDescriptor.h>
Mathias Agopian3cf61352010-02-09 17:46:37 -080039
40namespace android {
41
Igor Murashkinbef3f232013-05-30 17:47:38 -070042namespace {
43
44enum {
45 EX_SECURITY = -1,
46 EX_BAD_PARCELABLE = -2,
47 EX_ILLEGAL_ARGUMENT = -3,
48 EX_NULL_POINTER = -4,
49 EX_ILLEGAL_STATE = -5,
50 EX_HAS_REPLY_HEADER = -128, // special; see below
51};
52
53static bool readExceptionCode(Parcel& reply) {
54 int32_t exceptionCode = reply.readExceptionCode();
55
56 if (exceptionCode != 0) {
57 const char* errorMsg;
58 switch(exceptionCode) {
59 case EX_SECURITY:
60 errorMsg = "Security";
61 break;
62 case EX_BAD_PARCELABLE:
63 errorMsg = "BadParcelable";
64 break;
65 case EX_NULL_POINTER:
66 errorMsg = "NullPointer";
67 break;
68 case EX_ILLEGAL_STATE:
69 errorMsg = "IllegalState";
70 break;
71 // Binder should be handling this code inside Parcel::readException
72 // but lets have a to-string here anyway just in case.
73 case EX_HAS_REPLY_HEADER:
74 errorMsg = "HasReplyHeader";
75 break;
76 default:
77 errorMsg = "Unknown";
78 }
79
80 ALOGE("Binder transmission error %s (%d)", errorMsg, exceptionCode);
81 return true;
82 }
83
84 return false;
85}
86
87};
88
Mathias Agopian3cf61352010-02-09 17:46:37 -080089class BpCameraService: public BpInterface<ICameraService>
90{
91public:
92 BpCameraService(const sp<IBinder>& impl)
93 : BpInterface<ICameraService>(impl)
94 {
95 }
96
Chih-Chung Chang35a055b2010-05-06 16:36:58 +080097 // get number of cameras available
98 virtual int32_t getNumberOfCameras()
99 {
100 Parcel data, reply;
101 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
102 remote()->transact(BnCameraService::GET_NUMBER_OF_CAMERAS, data, &reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700103
104 if (readExceptionCode(reply)) return 0;
Chih-Chung Chang35a055b2010-05-06 16:36:58 +0800105 return reply.readInt32();
106 }
107
Chih-Chung Changddbdb352010-06-10 13:32:16 +0800108 // get information about a camera
109 virtual status_t getCameraInfo(int cameraId,
110 struct CameraInfo* cameraInfo) {
111 Parcel data, reply;
112 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
113 data.writeInt32(cameraId);
114 remote()->transact(BnCameraService::GET_CAMERA_INFO, data, &reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700115
116 if (readExceptionCode(reply)) return -EPROTO;
117 status_t result = reply.readInt32();
118 if (reply.readInt32() != 0) {
119 cameraInfo->facing = reply.readInt32();
120 cameraInfo->orientation = reply.readInt32();
121 }
122 return result;
Chih-Chung Changddbdb352010-06-10 13:32:16 +0800123 }
124
Zhijun He2b59be82013-09-25 10:14:30 -0700125 // get camera characteristics (static metadata)
126 virtual status_t getCameraCharacteristics(int cameraId,
127 CameraMetadata* cameraInfo) {
128 Parcel data, reply;
129 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
130 data.writeInt32(cameraId);
131 remote()->transact(BnCameraService::GET_CAMERA_CHARACTERISTICS, data, &reply);
132
133 if (readExceptionCode(reply)) return -EPROTO;
134 status_t result = reply.readInt32();
135
136 CameraMetadata out;
137 if (reply.readInt32() != 0) {
138 out.readFromParcel(&reply);
139 }
140
141 if (cameraInfo != NULL) {
142 cameraInfo->swap(out);
143 }
144
145 return result;
146 }
147
Ruben Brunkd1176ef2014-02-21 10:51:38 -0800148 // Get enumeration and description of vendor tags for camera
149 virtual status_t getCameraVendorTagDescriptor(/*out*/sp<VendorTagDescriptor>& desc) {
150 Parcel data, reply;
151 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
152 remote()->transact(BnCameraService::GET_CAMERA_VENDOR_TAG_DESCRIPTOR, data, &reply);
153
154 if (readExceptionCode(reply)) return -EPROTO;
155 status_t result = reply.readInt32();
156
157 if (reply.readInt32() != 0) {
158 sp<VendorTagDescriptor> d;
159 if (VendorTagDescriptor::createFromParcel(&reply, /*out*/d) == OK) {
160 desc = d;
161 }
162 }
163 return result;
164 }
165
Igor Murashkine7ee7632013-06-11 18:10:18 -0700166 // connect to camera service (android.hardware.Camera)
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700167 virtual status_t connect(const sp<ICameraClient>& cameraClient, int cameraId,
168 const String16 &clientPackageName, int clientUid,
169 /*out*/
170 sp<ICamera>& device)
Mathias Agopian3cf61352010-02-09 17:46:37 -0800171 {
172 Parcel data, reply;
173 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
174 data.writeStrongBinder(cameraClient->asBinder());
Chih-Chung Chang35a055b2010-05-06 16:36:58 +0800175 data.writeInt32(cameraId);
Eino-Ville Talvalaceb388d2013-02-19 10:40:14 -0800176 data.writeString16(clientPackageName);
177 data.writeInt32(clientUid);
Mathias Agopian3cf61352010-02-09 17:46:37 -0800178 remote()->transact(BnCameraService::CONNECT, data, &reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700179
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700180 if (readExceptionCode(reply)) return -EPROTO;
181 status_t status = reply.readInt32();
182 if (reply.readInt32() != 0) {
183 device = interface_cast<ICamera>(reply.readStrongBinder());
184 }
185 return status;
Mathias Agopian3cf61352010-02-09 17:46:37 -0800186 }
Igor Murashkin634a5152013-02-20 17:15:11 -0800187
188 // connect to camera service (pro client)
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700189 virtual status_t connectPro(const sp<IProCameraCallbacks>& cameraCb, int cameraId,
190 const String16 &clientPackageName, int clientUid,
191 /*out*/
192 sp<IProCameraUser>& device)
Igor Murashkin634a5152013-02-20 17:15:11 -0800193 {
194 Parcel data, reply;
195 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
196 data.writeStrongBinder(cameraCb->asBinder());
197 data.writeInt32(cameraId);
Igor Murashkinc073ba52013-02-26 14:32:34 -0800198 data.writeString16(clientPackageName);
199 data.writeInt32(clientUid);
Igor Murashkin634a5152013-02-20 17:15:11 -0800200 remote()->transact(BnCameraService::CONNECT_PRO, data, &reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700201
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700202 if (readExceptionCode(reply)) return -EPROTO;
203 status_t status = reply.readInt32();
204 if (reply.readInt32() != 0) {
205 device = interface_cast<IProCameraUser>(reply.readStrongBinder());
206 }
207 return status;
Igor Murashkin634a5152013-02-20 17:15:11 -0800208 }
Igor Murashkinbfc99152013-02-27 12:55:20 -0800209
Eino-Ville Talvala7b82efe2013-07-25 17:12:35 -0700210 // connect to camera service (android.hardware.camera2.CameraDevice)
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700211 virtual status_t connectDevice(
Igor Murashkine7ee7632013-06-11 18:10:18 -0700212 const sp<ICameraDeviceCallbacks>& cameraCb,
213 int cameraId,
214 const String16& clientPackageName,
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700215 int clientUid,
216 /*out*/
217 sp<ICameraDeviceUser>& device)
Igor Murashkine7ee7632013-06-11 18:10:18 -0700218 {
219 Parcel data, reply;
220 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
221 data.writeStrongBinder(cameraCb->asBinder());
222 data.writeInt32(cameraId);
223 data.writeString16(clientPackageName);
224 data.writeInt32(clientUid);
225 remote()->transact(BnCameraService::CONNECT_DEVICE, data, &reply);
226
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700227 if (readExceptionCode(reply)) return -EPROTO;
228 status_t status = reply.readInt32();
229 if (reply.readInt32() != 0) {
230 device = interface_cast<ICameraDeviceUser>(reply.readStrongBinder());
231 }
232 return status;
Igor Murashkine7ee7632013-06-11 18:10:18 -0700233 }
234
Igor Murashkinbfc99152013-02-27 12:55:20 -0800235 virtual status_t addListener(const sp<ICameraServiceListener>& listener)
236 {
237 Parcel data, reply;
238 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
239 data.writeStrongBinder(listener->asBinder());
240 remote()->transact(BnCameraService::ADD_LISTENER, data, &reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700241
242 if (readExceptionCode(reply)) return -EPROTO;
Igor Murashkinbfc99152013-02-27 12:55:20 -0800243 return reply.readInt32();
244 }
245
246 virtual status_t removeListener(const sp<ICameraServiceListener>& listener)
247 {
248 Parcel data, reply;
249 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor());
250 data.writeStrongBinder(listener->asBinder());
251 remote()->transact(BnCameraService::REMOVE_LISTENER, data, &reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700252
253 if (readExceptionCode(reply)) return -EPROTO;
Igor Murashkinbfc99152013-02-27 12:55:20 -0800254 return reply.readInt32();
255 }
Mathias Agopian3cf61352010-02-09 17:46:37 -0800256};
257
258IMPLEMENT_META_INTERFACE(CameraService, "android.hardware.ICameraService");
259
260// ----------------------------------------------------------------------
261
262status_t BnCameraService::onTransact(
263 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
264{
265 switch(code) {
Chih-Chung Chang35a055b2010-05-06 16:36:58 +0800266 case GET_NUMBER_OF_CAMERAS: {
267 CHECK_INTERFACE(ICameraService, data, reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700268 reply->writeNoException();
Chih-Chung Chang35a055b2010-05-06 16:36:58 +0800269 reply->writeInt32(getNumberOfCameras());
270 return NO_ERROR;
271 } break;
Chih-Chung Changddbdb352010-06-10 13:32:16 +0800272 case GET_CAMERA_INFO: {
273 CHECK_INTERFACE(ICameraService, data, reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700274 CameraInfo cameraInfo = CameraInfo();
Chih-Chung Changddbdb352010-06-10 13:32:16 +0800275 memset(&cameraInfo, 0, sizeof(cameraInfo));
276 status_t result = getCameraInfo(data.readInt32(), &cameraInfo);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700277 reply->writeNoException();
278 reply->writeInt32(result);
279
280 // Fake a parcelable object here
281 reply->writeInt32(1); // means the parcelable is included
Chih-Chung Changddbdb352010-06-10 13:32:16 +0800282 reply->writeInt32(cameraInfo.facing);
283 reply->writeInt32(cameraInfo.orientation);
Chih-Chung Changddbdb352010-06-10 13:32:16 +0800284 return NO_ERROR;
285 } break;
Zhijun He2b59be82013-09-25 10:14:30 -0700286 case GET_CAMERA_CHARACTERISTICS: {
287 CHECK_INTERFACE(ICameraService, data, reply);
288 CameraMetadata info;
289 status_t result = getCameraCharacteristics(data.readInt32(), &info);
290 reply->writeNoException();
291 reply->writeInt32(result);
292
293 // out-variables are after exception and return value
294 reply->writeInt32(1); // means the parcelable is included
295 info.writeToParcel(reply);
296 return NO_ERROR;
297 } break;
Ruben Brunkd1176ef2014-02-21 10:51:38 -0800298 case GET_CAMERA_VENDOR_TAG_DESCRIPTOR: {
299 CHECK_INTERFACE(ICameraService, data, reply);
300 sp<VendorTagDescriptor> d;
301 status_t result = getCameraVendorTagDescriptor(d);
302 reply->writeNoException();
303 reply->writeInt32(result);
304
305 // out-variables are after exception and return value
Ruben Brunkd1176ef2014-02-21 10:51:38 -0800306 if (d == NULL) {
307 reply->writeInt32(0);
308 } else {
Igor Murashkine1445da2014-03-17 14:00:29 -0700309 reply->writeInt32(1); // means the parcelable is included
Ruben Brunkd1176ef2014-02-21 10:51:38 -0800310 d->writeToParcel(reply);
311 }
312 return NO_ERROR;
313 } break;
Mathias Agopian3cf61352010-02-09 17:46:37 -0800314 case CONNECT: {
315 CHECK_INTERFACE(ICameraService, data, reply);
Eino-Ville Talvalaceb388d2013-02-19 10:40:14 -0800316 sp<ICameraClient> cameraClient =
317 interface_cast<ICameraClient>(data.readStrongBinder());
318 int32_t cameraId = data.readInt32();
319 const String16 clientName = data.readString16();
320 int32_t clientUid = data.readInt32();
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700321 sp<ICamera> camera;
322 status_t status = connect(cameraClient, cameraId,
Igor Murashkine1445da2014-03-17 14:00:29 -0700323 clientName, clientUid, /*out*/camera);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700324 reply->writeNoException();
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700325 reply->writeInt32(status);
326 if (camera != NULL) {
327 reply->writeInt32(1);
328 reply->writeStrongBinder(camera->asBinder());
329 } else {
330 reply->writeInt32(0);
331 }
Mathias Agopian3cf61352010-02-09 17:46:37 -0800332 return NO_ERROR;
333 } break;
Igor Murashkin634a5152013-02-20 17:15:11 -0800334 case CONNECT_PRO: {
335 CHECK_INTERFACE(ICameraService, data, reply);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700336 sp<IProCameraCallbacks> cameraClient =
337 interface_cast<IProCameraCallbacks>(data.readStrongBinder());
Igor Murashkinc073ba52013-02-26 14:32:34 -0800338 int32_t cameraId = data.readInt32();
339 const String16 clientName = data.readString16();
340 int32_t clientUid = data.readInt32();
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700341 sp<IProCameraUser> camera;
342 status_t status = connectPro(cameraClient, cameraId,
Igor Murashkine1445da2014-03-17 14:00:29 -0700343 clientName, clientUid, /*out*/camera);
Igor Murashkinbef3f232013-05-30 17:47:38 -0700344 reply->writeNoException();
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700345 reply->writeInt32(status);
346 if (camera != NULL) {
347 reply->writeInt32(1);
348 reply->writeStrongBinder(camera->asBinder());
349 } else {
350 reply->writeInt32(0);
351 }
Igor Murashkin634a5152013-02-20 17:15:11 -0800352 return NO_ERROR;
353 } break;
Igor Murashkine7ee7632013-06-11 18:10:18 -0700354 case CONNECT_DEVICE: {
355 CHECK_INTERFACE(ICameraService, data, reply);
356 sp<ICameraDeviceCallbacks> cameraClient =
357 interface_cast<ICameraDeviceCallbacks>(data.readStrongBinder());
358 int32_t cameraId = data.readInt32();
359 const String16 clientName = data.readString16();
360 int32_t clientUid = data.readInt32();
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700361 sp<ICameraDeviceUser> camera;
362 status_t status = connectDevice(cameraClient, cameraId,
Igor Murashkine1445da2014-03-17 14:00:29 -0700363 clientName, clientUid, /*out*/camera);
Igor Murashkine7ee7632013-06-11 18:10:18 -0700364 reply->writeNoException();
Ruben Brunk0f61d8f2013-08-08 13:07:18 -0700365 reply->writeInt32(status);
366 if (camera != NULL) {
367 reply->writeInt32(1);
368 reply->writeStrongBinder(camera->asBinder());
369 } else {
370 reply->writeInt32(0);
371 }
Igor Murashkine7ee7632013-06-11 18:10:18 -0700372 return NO_ERROR;
373 } break;
Igor Murashkinbfc99152013-02-27 12:55:20 -0800374 case ADD_LISTENER: {
375 CHECK_INTERFACE(ICameraService, data, reply);
376 sp<ICameraServiceListener> listener =
377 interface_cast<ICameraServiceListener>(data.readStrongBinder());
Igor Murashkinbef3f232013-05-30 17:47:38 -0700378 reply->writeNoException();
Igor Murashkinbfc99152013-02-27 12:55:20 -0800379 reply->writeInt32(addListener(listener));
380 return NO_ERROR;
381 } break;
382 case REMOVE_LISTENER: {
383 CHECK_INTERFACE(ICameraService, data, reply);
384 sp<ICameraServiceListener> listener =
385 interface_cast<ICameraServiceListener>(data.readStrongBinder());
Igor Murashkinbef3f232013-05-30 17:47:38 -0700386 reply->writeNoException();
Igor Murashkinbfc99152013-02-27 12:55:20 -0800387 reply->writeInt32(removeListener(listener));
388 return NO_ERROR;
389 } break;
Mathias Agopian3cf61352010-02-09 17:46:37 -0800390 default:
391 return BBinder::onTransact(code, data, reply, flags);
392 }
393}
394
395// ----------------------------------------------------------------------------
396
397}; // namespace android