blob: 08062ec8bc515ed78a287b3a159cd6deb7ccf912 [file] [log] [blame]
/*
* Copyright (C) 2015-2020 Intel Corporation.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#pragma once
#include <map>
#include <vector>
#include "iutils/Thread.h"
#include "StreamSource.h"
#include "CameraBuffer.h"
#include "DeviceBase.h"
#include "IspParamAdaptor.h"
namespace icamera {
/**
* CaptureUnit abstract the ISYS function.
* It implements the BufferProducer Interface and it is the source of any pipeline
* It hides the v4l2 and media controller to the upper layer.
*/
class CaptureUnit : public StreamSource, public DeviceCallback {
public:
CaptureUnit(int cameraId, int memType = V4L2_MEMORY_MMAP);
virtual ~CaptureUnit();
public:
/**
* \brief Queue on buffer to driver
*
* 1. Get the v4l2 buffer form the CameraBuffer
* 2. Queue this v4l2 buffer to driver and save it to one queue.
*
* \param[in] port: Indicates the camBuffer belongs to which port
* \param[in] camBuffer: the cameraBuffer queue to driver
*
* \return 0 if succeed, other value indicates failed
*/
virtual int qbuf(Port port, const std::shared_ptr<CameraBuffer> &camBuffer);
/**
* \brief allocate memory
*
* 1. Get the v4l2 buffer form the CameraBuffer
* 2. Query the v4l2 buffer to get the offset
* 3. Calling cameraBuffer class to allocate memory
*
* \return OK if succeed, other value indicates failed
*/
virtual int allocateMemory(Port port, const std::shared_ptr<CameraBuffer> &camBuffer);
/**
* \brief Add the frame buffer listener
*
* \param listener: the listener need to add
*/
virtual void addFrameAvailableListener(BufferConsumer *listener);
/**
* \brief Remove the frame buffer listener
*
* \param listener: the listener need to remove
*/
virtual void removeFrameAvailableListener(BufferConsumer *listener);
/**
* \brief Remove all the listeners
*/
virtual void removeAllFrameAvailableListener();
/**
* \brief CaptureUnit initialze
*/
virtual int init();
/**
* \brief CaptureUnit deinit
*
* 1. Destory all the buffer pool
* 2. Deinit the v4l2 device
* 3. Destory the poll thread
*/
virtual void deinit();
/**
* \brief CaptureUnit start
*
* 1. Stream on
* 2. Running the pool Thread
*/
virtual int start();
/**
* \brief CaptureUnit stop
*
* 1. Stream off
* 3. Release all the buffer queue
* 3. Stop the pool thread.
*/
virtual int stop();
/**
* \brief configure the streams
*
* 1. Setup and reset the MediaControl links
* 2. Set format to Capture Device
*
* \param outputFrames: The output frames' configuration for ISYS.
* \param configModes: ConfigMode types
*
* \return OK if succeed, other value indicates failed
*/
virtual int configure(const std::map<Port, stream_t>& outputFrames,
const std::vector<ConfigMode>& configModes);
// Override EventSource API to delegate the listeners to DeviceBase.
virtual void registerListener(EventType eventType, EventListener* eventListener);
virtual void removeListener(EventType eventType, EventListener* eventListener);
// Overwrite DeviceCallback API
void onDequeueBuffer();
private:
DISALLOW_COPY_AND_ASSIGN(CaptureUnit);
int createDevices();
void destroyDevices();
DeviceBase* findDeviceByPort(Port port);
Port findDefaultPort(const std::map<Port, stream_t>& frames) const;
int streamOn();
void streamOff();
int poll();
bool isNewConfiguration(const std::map<Port, stream_t>& outputFrames);
int processPendingBuffers();
int queueAllBuffers();
private:
/**
* \brief The pool frame buffer thread
*/
class PollThread: public Thread {
CaptureUnit *mCaptureU;
public:
PollThread(CaptureUnit *hw) : mCaptureU(hw) { }
virtual bool threadLoop() {
return (mCaptureU->poll() == 0);
}
};
PollThread* mPollThread;
// Guard for mCaptureUnit public API except dqbuf and qbuf
Mutex mLock;
int mCameraId;
int mMaxBuffersInDevice; // To control the number of buffers enqueued, for per-frame control.
std::vector<ConfigMode> mConfigModes;
std::map<Port, stream_t> mOutputFrameInfo;
DeviceBase* mDevice;
uint32_t mMaxBufferNum;
enum {
CAPTURE_UNINIT,
CAPTURE_INIT,
CAPTURE_CONFIGURE,
CAPTURE_START,
CAPTURE_STOP,
} mState;
bool mExitPending;
};
} // namespace icamera