ronnie
2022-10-14 1504bb53e29d3d46222c0b3ea994fc494b48e153
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
/*
 * Copyright (c) 2021 by Allwinnertech Co., Ltd.
 *
 * 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.
 */
 
#ifndef V4L2_CAMERA_HAL_V4L2_STREAM_H_
#define V4L2_CAMERA_HAL_V4L2_STREAM_H_
 
#include "common.h"
#ifdef LOG_NDEBUG
#undef LOG_NDEBUG
#endif
 
#if DBG_V4L2_STREAM
#undef NDEBUG
#define LOG_NDEBUG 0
#else
#define LOG_NDEBUG 1
#endif
 
#include <android-base/unique_fd.h>
#include <utils/StrongPointer.h>
#include <utils/RefBase.h>
#include <sys/epoll.h>
#include <sunxi_camera_v2.h>
 
#include <array>
#include <functional>
#include <memory>
#include <mutex>
#include <queue>
#include <set>
#include <string>
#include <utility>
#include <vector>
 
#include "common.h"
#include "stream_format.h"
#include "v4l2_gralloc.h"
#include "v4l2_wrapper.h"
#include "camera_config.h"
#include "camera_stream.h"
#include "type_camera.h"
 
#ifdef USE_ISP
#include "AWIspApi.h"
#endif
 
namespace v4l2_camera_hal {
 
class V4L2Stream : public virtual android::RefBase  {
  friend class V4L2Wrapper;
  friend class ConnectionStream;
 public:
  // Use this method to create V4L2Stream objects. Functionally equivalent
  // to "new V4L2Stream", except that it may return nullptr in case of failure.
  static V4L2Stream* NewV4L2Stream(const int id,
                                   const std::string device_path,
                                   std::shared_ptr<CCameraConfig> pCameraCfg);
  virtual ~V4L2Stream();
 
  // Turn the stream on or off.
  virtual int StreamOn();
  virtual int StreamOff();
  virtual int flush();
  // Manage controls.
  virtual int QueryControl(uint32_t control_id, v4l2_query_ext_ctrl* result);
  virtual int GetControl(uint32_t control_id, int32_t* value);
  virtual int SetControl(uint32_t control_id,
                         int32_t desired,
                         int32_t* result = nullptr);
  virtual int SetFlashMode(uint32_t mode);
  virtual int SetTakePictureCtrl(enum v4l2_take_picture value);
  virtual int SetAutoFocusInit();
  virtual int SetAutoFocusRange(int af_range);
  virtual int SetAutoFocusStart();
  virtual int SetAutoFocusStop();
  virtual int Set3ALock(int lock);
  virtual int GetAutoFocusStatus();
  virtual int SetAutoFocusRegions(cam_rect_t cam_regions);
  virtual int SetCropRect(cam_crop_rect_t cam_crop_rect);
  virtual int SetJpegCropRect(cam_crop_rect_t cam_crop_rect);
  virtual int SetParm(int mCapturemode);
  // Manage format.
  virtual int GetFormats(std::set<uint32_t>* v4l2_formats);
  virtual int GetFormatFrameSizes(uint32_t v4l2_format,
                                  std::set<std::array<int32_t, 2>,
                                  std::greater<std::array<int32_t, 2>>>* sizes);
 
  // Durations are returned in ns.
  virtual int GetFormatFrameDurationRange(
      uint32_t v4l2_format,
      const std::array<int32_t, 2>& size,
      std::array<int64_t, 2>* duration_range);
  virtual int SetFormat(const StreamFormat& desired_format,
                        uint32_t* result_max_buffers);
  // Manage buffers.
  virtual int PrepareBuffer();
  virtual int WaitCameraReady();
  virtual int EnqueueBuffer();
  virtual int DequeueBuffer(void ** src_addr_, struct timeval * ts);
  virtual int CopyYCbCrBuffer(android_ycbcr* dst_addr_ycbcr, void* src_addr);
  virtual int EncodeBuffer(void * dst_addr,
                           void * src_addr,
                           unsigned long mJpegBufferSizes,
                           JPEG_ENC_t jpeg_enc);
  virtual int queueBuffer(v4l2_buffer* pdevice_buffer);
  virtual int dequeueBuffer(v4l2_buffer* pdevice_buffer);
 
  // Tools.
  int GetDeviceId() {return device_id_;}
  int GetDeviceWidth() {return format_->width();}
  int GetDeviceHeight() {return format_->height();}
 
  STREAM_SERIAL getStreamSerial() {return device_ss_;}
 
 
 private:
  std::shared_ptr<CCameraConfig> mCameraConfig;
  // Constructor is private to allow failing on bad input.
  // Use NewV4L2Stream instead.
  V4L2Stream(const int id,
             const std::string device_path,
             std::shared_ptr<CCameraConfig> pCameraCfg);
 
  // Connect or disconnect to the device. Access by creating/destroying
  // a V4L2Wrapper::Connection object.
  int Connect();
  void Disconnect();
  // Perform an ioctl call in a thread-safe fashion.
  template <typename T>
  int IoctlLocked(int request, T data);
  // Request/release userspace buffer mode via VIDIOC_REQBUFS.
  int RequestBuffers(uint32_t num_buffers);
 
  inline bool connected() { return device_fd_ >= 0; }
 
  int parse_pair(const char *str,
                 uint32_t *first,
                 uint32_t *second,
                 char delim);
  void initV4l2Str();
 
  // The camera device path. For example, /dev/video0.
  const std::string device_path_;
  STREAM_SERIAL device_ss_;
 
  int device_fd_;
  // Pipe for wakeup epoll
  int read_fd_;
  int write_fd_;
  bool disconnect;
 
  cam_crop_rect_t jpeg_crop_rect;
 
  epoll_event *pEvents;
  // The open camera facing.
  const int device_id_;
 
  // Whether or not the device supports the extended control query.
  bool extended_query_supported_;
  // The format this device is set up for.
  std::unique_ptr<StreamFormat> format_;
 
  unsigned long  mTimeStampsFstreamon;
  //
  bool has_StreamOn;
  //
  bool mflush_buffers;
  bool isTakePicture;
  enum {
    BUFFER_UNINIT,
    BUFFER_PREPARE,
    BUFFER_QUEUE,
    BUFFER_DEQUEUE
  } buffer_state_;
  // Map indecies to buffer status. True if the index is in-flight.
  // |buffers_.size()| will always be the maximum number of buffers this device
  // can handle in its current format.
  std::vector<bool> buffers_pstream_;
 
  // Map indecies to buffer status. True if the index is in-flight.
  // |buffers_.size()| will always be the maximum number of buffers this device
  // can handle in its current format.
  std::vector<bool> buffers_;
 
  // Lock protecting use of the buffer tracker.
  std::mutex buffer_queue_lock_;
  std::mutex aw_ve_lock;
  std::queue<int>buffers_num_;
  std::condition_variable buffer_availabl_queue_;
 
 
  // Buffer manager.
  std::mutex cmd_queue_lock_;
  int buffer_cnt_inflight_;
  // Lock protecting use of the device.
  std::mutex device_lock_;
  // Debug tools for save buffers.
  void * buffers_addr[MAX_BUFFER_NUM];
  int buffers_fd[MAX_BUFFER_NUM];
 
  typedef struct v4l2_mem_map_t{
      void *    mem[MAX_BUFFER_NUM];
      int     length;
      int             nShareBufFd[MAX_BUFFER_NUM];
      int             nDmaBufFd[MAX_BUFFER_NUM];
  }v4l2_mem_map_t;
  v4l2_mem_map_t                    mMapMem;
 
  enum {
      CAMERA3_JPEG_3A_PARAM_BLOB_ID = 0xAAFFAAFF,
      CAMERA3_JPEG_ISP_MSG_BLOB_ID = 0xABFFABFF,
  };
 
  typedef struct camera3_jpeg_3a_blob {
      uint32_t jpeg_3a_header_id;
      uint32_t jpeg_3a_size;
      char     magic_str[8];
  } camera3_jpeg_3a_blob_t;
 
  typedef struct camera3_jpeg_isp_msg_blob {
      uint32_t jpeg_isp_msg_header_id;
      uint32_t jpeg_isp_msg_size;
      char     magic_str[8];
  } camera3_jpeg_isp_msg_blob_t;
 
#ifdef USE_ISP
  android::AWIspApi                          *mAWIspApi;
  int                               mIspId;
#endif
 
  // Lock protecting connecting/disconnecting the device.
  std::mutex connection_lock_;
  // Reference count connections.
  int connection_count_;
  friend class Connection;
#ifdef USE_ISP
  friend class android::AWIspApi;
#endif
 
  DISALLOW_COPY_AND_ASSIGN(V4L2Stream);
};
 
// Helper class to ensure all opened connections are closed.
class ConnectionStream {
  friend class V4L2Stream;
 public:
  explicit ConnectionStream(std::shared_ptr<V4L2Stream> device)
      : device_(std::move(device)) {
      connect_result_ = device_->Connect();
  }
  ~ConnectionStream() {
    if (connect_result_ == 0) {
      device_->Disconnect();
    }
  }
  // Check whether the connection succeeded or not.
  inline int status() const { return connect_result_; }
 
 private:
  std::shared_ptr<V4L2Stream> device_;
  int connect_result_;
  DISALLOW_COPY_AND_ASSIGN(ConnectionStream);
};
 
}  // namespace v4l2_camera_hal
 
#endif  // V4L2_CAMERA_HAL_V4L2_WRAPPER_H_