ProCamera.h revision 4bc4a3845e456fd464556d79d20650a107e873e5
1/* 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#ifndef ANDROID_HARDWARE_PRO_CAMERA_H 18#define ANDROID_HARDWARE_PRO_CAMERA_H 19 20#include <utils/Timers.h> 21#include <utils/KeyedVector.h> 22#include <gui/IGraphicBufferProducer.h> 23#include <system/camera.h> 24#include <camera/IProCameraCallbacks.h> 25#include <camera/IProCameraUser.h> 26#include <camera/Camera.h> 27#include <camera/CameraMetadata.h> 28#include <gui/CpuConsumer.h> 29 30#include <utils/Condition.h> 31#include <utils/Mutex.h> 32 33struct camera_metadata; 34 35namespace android { 36 37// All callbacks on this class are concurrent 38// (they come from separate threads) 39class ProCameraListener : public CameraListener 40{ 41public: 42 // Lock has been acquired. Write operations now available. 43 virtual void onLockAcquired() = 0; 44 // Lock has been released with exclusiveUnlock. 45 virtual void onLockReleased() = 0; 46 // Lock has been stolen by another client. 47 virtual void onLockStolen() = 0; 48 49 // Lock free. 50 virtual void onTriggerNotify(int32_t msgType, int32_t ext1, int32_t ext2) 51 = 0; 52 53 // OnBufferReceived and OnRequestReceived can come in with any order, 54 // use android.sensor.timestamp and LockedBuffer.timestamp to correlate them 55 56 // A new frame buffer has been received for this stream. 57 // -- This callback only fires for createStreamCpu streams 58 // -- Use buf.timestamp to correlate with metadata's 59 // android.sensor.timestamp 60 // -- The buffer must not be accessed after this function call completes 61 virtual void onBufferReceived(int streamId, 62 const CpuConsumer::LockedBuffer& buf) = 0; 63 /** 64 * A new metadata buffer has been received. 65 * -- Ownership of request passes on to the callee, free with 66 * free_camera_metadata. 67 */ 68 virtual void onResultReceived(int32_t frameId, camera_metadata* result) = 0; 69 70 71 // A new frame buffer has been received for this stream. 72 // -- This callback only fires for createStreamCpu streams 73 // -- Use buf.timestamp to correlate with metadata's android.sensor.timestamp 74 // -- The buffer should be accessed with CpuConsumer::lockNextBuffer 75 // and CpuConsumer::unlockBuffer 76 virtual void onFrameAvailable(int streamId, 77 const sp<CpuConsumer>& cpuConsumer) { 78 } 79 80 virtual bool useOnFrameAvailable() { 81 return false; 82 } 83}; 84 85class ProCamera : public BnProCameraCallbacks, public IBinder::DeathRecipient 86{ 87public: 88 /** 89 * Connect a shared camera. By default access is restricted to read only 90 * (Lock free) operations. To be able to submit custom requests a lock needs 91 * to be acquired with exclusive[Try]Lock. 92 */ 93 static sp<ProCamera> connect(int cameraId); 94 virtual void disconnect(); 95 virtual ~ProCamera(); 96 97 void setListener(const sp<ProCameraListener>& listener); 98 99 /** 100 * Exclusive Locks: 101 * - We may request exclusive access to a camera if no other 102 * clients are using the camera. This works as a traditional 103 * client, writing/reading any camera state. 104 * - An application opening the camera (a regular 'Camera') will 105 * always steal away the exclusive lock from a ProCamera, 106 * this will call onLockReleased. 107 * - onLockAcquired will be called again once it is possible 108 * to again exclusively lock the camera. 109 * 110 */ 111 112 /** 113 * All exclusiveLock/unlock functions are asynchronous. The remote endpoint 114 * shall not block while waiting to acquire the lock. Instead the lock 115 * notifications will come in asynchronously on the listener. 116 */ 117 118 /** 119 * Attempt to acquire the lock instantly (non-blocking) 120 * - If this succeeds, you do not need to wait for onLockAcquired 121 * but the event will still be fired 122 * 123 * Returns -EBUSY if already locked. 0 on success. 124 */ 125 status_t exclusiveTryLock(); 126 // always returns 0. wait for onLockAcquired before lock is acquired. 127 status_t exclusiveLock(); 128 // release a lock if we have one, or cancel the lock request. 129 status_t exclusiveUnlock(); 130 131 // exclusive lock = do whatever we want. no lock = read only. 132 bool hasExclusiveLock(); 133 134 /** 135 * < 0 error, >= 0 the request ID. streaming to have the request repeat 136 * until cancelled. 137 * The request queue is flushed when a lock is released or stolen 138 * if not locked will return PERMISSION_DENIED 139 */ 140 int submitRequest(const struct camera_metadata* metadata, 141 bool streaming = false); 142 // if not locked will return PERMISSION_DENIED, BAD_VALUE if requestId bad 143 status_t cancelRequest(int requestId); 144 145 /** 146 * Ask for a stream to be enabled. 147 * Lock free. Service maintains counter of streams. 148 */ 149 status_t requestStream(int streamId); 150// TODO: remove requestStream, its useless. 151 152 /** 153 * Delete a stream. 154 * Lock free. 155 * Errors: BAD_VALUE if unknown stream ID. 156 * PERMISSION_DENIED if the stream wasn't yours 157 */ 158 status_t deleteStream(int streamId); 159 160 /** 161 * Create a new HW stream, whose sink will be the window. 162 * Lock free. Service maintains counter of streams. 163 * Errors: -EBUSY if too many streams created 164 */ 165 status_t createStream(int width, int height, int format, 166 const sp<Surface>& surface, 167 /*out*/ 168 int* streamId); 169 170 /** 171 * Create a new HW stream, whose sink will be the SurfaceTexture. 172 * Lock free. Service maintains counter of streams. 173 * Errors: -EBUSY if too many streams created 174 */ 175 status_t createStream(int width, int height, int format, 176 const sp<IGraphicBufferProducer>& bufferProducer, 177 /*out*/ 178 int* streamId); 179 status_t createStreamCpu(int width, int height, int format, 180 int heapCount, 181 /*out*/ 182 sp<CpuConsumer>* cpuConsumer, 183 int* streamId); 184 185 // Create a request object from a template. 186 status_t createDefaultRequest(int templateId, 187 /*out*/ 188 camera_metadata** request) const; 189 190 // Get number of cameras 191 static int getNumberOfCameras(); 192 193 // Get static camera metadata 194 camera_metadata* getCameraInfo(int cameraId); 195 196 // Blocks until a frame is available (CPU streams only) 197 // - Obtain the frame data by calling CpuConsumer::lockNextBuffer 198 // - Release the frame data after use with CpuConsumer::unlockBuffer 199 // Return value: 200 // - >0 - number of frames available to be locked 201 // - <0 - error (refer to error codes) 202 // Error codes: 203 // -ETIMEDOUT if it took too long to get a frame 204 int waitForFrameBuffer(int streamId); 205 206 // Blocks until a metadata result is available 207 // - Obtain the metadata by calling consumeFrameMetadata() 208 // Error codes: 209 // -ETIMEDOUT if it took too long to get a frame 210 status_t waitForFrameMetadata(); 211 212 // Get the latest metadata. This is destructive. 213 // - Calling this repeatedly will produce empty metadata objects. 214 // - Use waitForFrameMetadata to sync until new data is available. 215 CameraMetadata consumeFrameMetadata(); 216 217 // Convenience method to drop frame buffers (CPU streams only) 218 // Return values: 219 // >=0 - number of frames dropped (up to count) 220 // <0 - error code 221 // Error codes: 222 // BAD_VALUE - invalid streamId or count passed 223 int dropFrameBuffer(int streamId, int count); 224 225 sp<IProCameraUser> remote(); 226 227protected: 228 //////////////////////////////////////////////////////// 229 // IProCameraCallbacks implementation 230 //////////////////////////////////////////////////////// 231 virtual void notifyCallback(int32_t msgType, int32_t ext, 232 int32_t ext2); 233 virtual void dataCallback(int32_t msgType, 234 const sp<IMemory>& dataPtr, 235 camera_frame_metadata_t *metadata); 236 virtual void dataCallbackTimestamp(nsecs_t timestamp, 237 int32_t msgType, 238 const sp<IMemory>& dataPtr); 239 virtual void onLockStatusChanged( 240 IProCameraCallbacks::LockStatus newLockStatus); 241 242 virtual void onResultReceived(int32_t frameId, 243 camera_metadata* result); 244 245 class DeathNotifier: public IBinder::DeathRecipient 246 { 247 public: 248 DeathNotifier() { 249 } 250 251 virtual void binderDied(const wp<IBinder>& who); 252 }; 253 254private: 255 ProCamera(); 256 257 virtual void binderDied(const wp<IBinder>& who); 258 259 // helper function to obtain camera service handle 260 static const sp<ICameraService>& getCameraService(); 261 262 static sp<DeathNotifier> mDeathNotifier; 263 264 sp<IProCameraUser> mCamera; 265 status_t mStatus; 266 267 sp<ProCameraListener> mListener; 268 269 friend class DeathNotifier; 270 271 static Mutex mLock; 272 static sp<ICameraService> mCameraService; 273 274 class ProFrameListener : public CpuConsumer::FrameAvailableListener { 275 public: 276 ProFrameListener(wp<ProCamera> camera, int streamID) { 277 mCamera = camera; 278 mStreamId = streamID; 279 } 280 281 protected: 282 virtual void onFrameAvailable() { 283 sp<ProCamera> c = mCamera.promote(); 284 if (c.get() != NULL) { 285 c->onFrameAvailable(mStreamId); 286 } 287 } 288 289 private: 290 wp<ProCamera> mCamera; 291 int mStreamId; 292 }; 293 friend class ProFrameListener; 294 295 struct StreamInfo 296 { 297 StreamInfo(int streamId) { 298 this->streamID = streamId; 299 cpuStream = false; 300 frameReady = 0; 301 } 302 303 StreamInfo() { 304 streamID = -1; 305 cpuStream = false; 306 } 307 308 int streamID; 309 bool cpuStream; 310 sp<CpuConsumer> cpuConsumer; 311 sp<ProFrameListener> frameAvailableListener; 312 sp<Surface> stc; 313 int frameReady; 314 }; 315 316 Condition mWaitCondition; 317 Mutex mWaitMutex; 318 static const nsecs_t mWaitTimeout = 1000000000; // 1sec 319 KeyedVector<int, StreamInfo> mStreams; 320 bool mMetadataReady; 321 CameraMetadata mLatestMetadata; 322 323 void onFrameAvailable(int streamId); 324 325 StreamInfo& getStreamInfo(int streamId); 326 327 328}; 329 330}; // namespace android 331 332#endif 333