ICameraService.cpp revision e7ee7637747371635a85fedd24d2190bb1f38651
1/* 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 18#define LOG_TAG "BpCameraService" 19#include <utils/Log.h> 20 21#include <stdint.h> 22#include <sys/types.h> 23 24#include <binder/Parcel.h> 25#include <binder/IPCThreadState.h> 26#include <binder/IServiceManager.h> 27 28#include <camera/ICameraService.h> 29#include <camera/ICameraServiceListener.h> 30#include <camera/IProCameraUser.h> 31#include <camera/IProCameraCallbacks.h> 32#include <camera/ICamera.h> 33#include <camera/ICameraClient.h> 34#include <camera/photography/ICameraDeviceUser.h> 35#include <camera/photography/ICameraDeviceCallbacks.h> 36 37namespace android { 38 39namespace { 40 41enum { 42 EX_SECURITY = -1, 43 EX_BAD_PARCELABLE = -2, 44 EX_ILLEGAL_ARGUMENT = -3, 45 EX_NULL_POINTER = -4, 46 EX_ILLEGAL_STATE = -5, 47 EX_HAS_REPLY_HEADER = -128, // special; see below 48}; 49 50static bool readExceptionCode(Parcel& reply) { 51 int32_t exceptionCode = reply.readExceptionCode(); 52 53 if (exceptionCode != 0) { 54 const char* errorMsg; 55 switch(exceptionCode) { 56 case EX_SECURITY: 57 errorMsg = "Security"; 58 break; 59 case EX_BAD_PARCELABLE: 60 errorMsg = "BadParcelable"; 61 break; 62 case EX_NULL_POINTER: 63 errorMsg = "NullPointer"; 64 break; 65 case EX_ILLEGAL_STATE: 66 errorMsg = "IllegalState"; 67 break; 68 // Binder should be handling this code inside Parcel::readException 69 // but lets have a to-string here anyway just in case. 70 case EX_HAS_REPLY_HEADER: 71 errorMsg = "HasReplyHeader"; 72 break; 73 default: 74 errorMsg = "Unknown"; 75 } 76 77 ALOGE("Binder transmission error %s (%d)", errorMsg, exceptionCode); 78 return true; 79 } 80 81 return false; 82} 83 84}; 85 86class BpCameraService: public BpInterface<ICameraService> 87{ 88public: 89 BpCameraService(const sp<IBinder>& impl) 90 : BpInterface<ICameraService>(impl) 91 { 92 } 93 94 // get number of cameras available 95 virtual int32_t getNumberOfCameras() 96 { 97 Parcel data, reply; 98 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 99 remote()->transact(BnCameraService::GET_NUMBER_OF_CAMERAS, data, &reply); 100 101 if (readExceptionCode(reply)) return 0; 102 return reply.readInt32(); 103 } 104 105 // get information about a camera 106 virtual status_t getCameraInfo(int cameraId, 107 struct CameraInfo* cameraInfo) { 108 Parcel data, reply; 109 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 110 data.writeInt32(cameraId); 111 remote()->transact(BnCameraService::GET_CAMERA_INFO, data, &reply); 112 113 if (readExceptionCode(reply)) return -EPROTO; 114 status_t result = reply.readInt32(); 115 if (reply.readInt32() != 0) { 116 cameraInfo->facing = reply.readInt32(); 117 cameraInfo->orientation = reply.readInt32(); 118 } 119 return result; 120 } 121 122 // connect to camera service (android.hardware.Camera) 123 virtual sp<ICamera> connect(const sp<ICameraClient>& cameraClient, int cameraId, 124 const String16 &clientPackageName, int clientUid) 125 { 126 Parcel data, reply; 127 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 128 data.writeStrongBinder(cameraClient->asBinder()); 129 data.writeInt32(cameraId); 130 data.writeString16(clientPackageName); 131 data.writeInt32(clientUid); 132 remote()->transact(BnCameraService::CONNECT, data, &reply); 133 134 if (readExceptionCode(reply)) return NULL; 135 return interface_cast<ICamera>(reply.readStrongBinder()); 136 } 137 138 // connect to camera service (pro client) 139 virtual sp<IProCameraUser> connect(const sp<IProCameraCallbacks>& cameraCb, int cameraId, 140 const String16 &clientPackageName, int clientUid) 141 { 142 Parcel data, reply; 143 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 144 data.writeStrongBinder(cameraCb->asBinder()); 145 data.writeInt32(cameraId); 146 data.writeString16(clientPackageName); 147 data.writeInt32(clientUid); 148 remote()->transact(BnCameraService::CONNECT_PRO, data, &reply); 149 150 if (readExceptionCode(reply)) return NULL; 151 return interface_cast<IProCameraUser>(reply.readStrongBinder()); 152 } 153 154 // connect to camera service (android.hardware.photography.CameraDevice) 155 virtual sp<ICameraDeviceUser> connect( 156 const sp<ICameraDeviceCallbacks>& cameraCb, 157 int cameraId, 158 const String16& clientPackageName, 159 int clientUid) 160 { 161 Parcel data, reply; 162 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 163 data.writeStrongBinder(cameraCb->asBinder()); 164 data.writeInt32(cameraId); 165 data.writeString16(clientPackageName); 166 data.writeInt32(clientUid); 167 remote()->transact(BnCameraService::CONNECT_DEVICE, data, &reply); 168 169 if (readExceptionCode(reply)) return NULL; 170 return interface_cast<ICameraDeviceUser>(reply.readStrongBinder()); 171 } 172 173 virtual status_t addListener(const sp<ICameraServiceListener>& listener) 174 { 175 Parcel data, reply; 176 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 177 data.writeStrongBinder(listener->asBinder()); 178 remote()->transact(BnCameraService::ADD_LISTENER, data, &reply); 179 180 if (readExceptionCode(reply)) return -EPROTO; 181 return reply.readInt32(); 182 } 183 184 virtual status_t removeListener(const sp<ICameraServiceListener>& listener) 185 { 186 Parcel data, reply; 187 data.writeInterfaceToken(ICameraService::getInterfaceDescriptor()); 188 data.writeStrongBinder(listener->asBinder()); 189 remote()->transact(BnCameraService::REMOVE_LISTENER, data, &reply); 190 191 if (readExceptionCode(reply)) return -EPROTO; 192 return reply.readInt32(); 193 } 194}; 195 196IMPLEMENT_META_INTERFACE(CameraService, "android.hardware.ICameraService"); 197 198// ---------------------------------------------------------------------- 199 200status_t BnCameraService::onTransact( 201 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags) 202{ 203 switch(code) { 204 case GET_NUMBER_OF_CAMERAS: { 205 CHECK_INTERFACE(ICameraService, data, reply); 206 reply->writeNoException(); 207 reply->writeInt32(getNumberOfCameras()); 208 return NO_ERROR; 209 } break; 210 case GET_CAMERA_INFO: { 211 CHECK_INTERFACE(ICameraService, data, reply); 212 CameraInfo cameraInfo = CameraInfo(); 213 memset(&cameraInfo, 0, sizeof(cameraInfo)); 214 status_t result = getCameraInfo(data.readInt32(), &cameraInfo); 215 reply->writeNoException(); 216 reply->writeInt32(result); 217 218 // Fake a parcelable object here 219 reply->writeInt32(1); // means the parcelable is included 220 reply->writeInt32(cameraInfo.facing); 221 reply->writeInt32(cameraInfo.orientation); 222 return NO_ERROR; 223 } break; 224 case CONNECT: { 225 CHECK_INTERFACE(ICameraService, data, reply); 226 sp<ICameraClient> cameraClient = 227 interface_cast<ICameraClient>(data.readStrongBinder()); 228 int32_t cameraId = data.readInt32(); 229 const String16 clientName = data.readString16(); 230 int32_t clientUid = data.readInt32(); 231 sp<ICamera> camera = connect(cameraClient, cameraId, 232 clientName, clientUid); 233 reply->writeNoException(); 234 reply->writeStrongBinder(camera->asBinder()); 235 return NO_ERROR; 236 } break; 237 case CONNECT_PRO: { 238 CHECK_INTERFACE(ICameraService, data, reply); 239 sp<IProCameraCallbacks> cameraClient = 240 interface_cast<IProCameraCallbacks>(data.readStrongBinder()); 241 int32_t cameraId = data.readInt32(); 242 const String16 clientName = data.readString16(); 243 int32_t clientUid = data.readInt32(); 244 sp<IProCameraUser> camera = connect(cameraClient, cameraId, 245 clientName, clientUid); 246 reply->writeNoException(); 247 reply->writeStrongBinder(camera->asBinder()); 248 return NO_ERROR; 249 } break; 250 case CONNECT_DEVICE: { 251 CHECK_INTERFACE(ICameraService, data, reply); 252 sp<ICameraDeviceCallbacks> cameraClient = 253 interface_cast<ICameraDeviceCallbacks>(data.readStrongBinder()); 254 int32_t cameraId = data.readInt32(); 255 const String16 clientName = data.readString16(); 256 int32_t clientUid = data.readInt32(); 257 sp<ICameraDeviceUser> camera = connect(cameraClient, cameraId, 258 clientName, clientUid); 259 reply->writeNoException(); 260 reply->writeStrongBinder(camera->asBinder()); 261 return NO_ERROR; 262 } break; 263 case ADD_LISTENER: { 264 CHECK_INTERFACE(ICameraService, data, reply); 265 sp<ICameraServiceListener> listener = 266 interface_cast<ICameraServiceListener>(data.readStrongBinder()); 267 reply->writeNoException(); 268 reply->writeInt32(addListener(listener)); 269 return NO_ERROR; 270 } break; 271 case REMOVE_LISTENER: { 272 CHECK_INTERFACE(ICameraService, data, reply); 273 sp<ICameraServiceListener> listener = 274 interface_cast<ICameraServiceListener>(data.readStrongBinder()); 275 reply->writeNoException(); 276 reply->writeInt32(removeListener(listener)); 277 return NO_ERROR; 278 } break; 279 default: 280 return BBinder::onTransact(code, data, reply, flags); 281 } 282} 283 284// ---------------------------------------------------------------------------- 285 286}; // namespace android 287