1 /*
2 ** Copyright (c) 2011-2012 The Linux Foundation. All rights reserved.
3 **
4 ** Not a Contribution, Apache license notifications and license are retained
5 ** for attribution purposes only.
6 **
7 ** Licensed under the Apache License, Version 2.0 (the "License");
8 ** you may not use this file except in compliance with the License.
9 ** You may obtain a copy of the License at
10 **
11 **     http://www.apache.org/licenses/LICENSE-2.0
12 **
13 ** Unless required by applicable law or agreed to in writing, software
14 ** distributed under the License is distributed on an "AS IS" BASIS,
15 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 ** See the License for the specific language governing permissions and
17 ** limitations under the License.
18 */
19 
20 /*#error uncomment this for compiler test!*/
21 
22 #define LOG_TAG "QCameraHWI_Rdi"
23 #include <utils/Log.h>
24 #include <utils/threads.h>
25 #include <fcntl.h>
26 #include <sys/mman.h>
27 #include "QCameraHAL.h"
28 #include "QCameraHWI.h"
29 #include <gralloc_priv.h>
30 #include <genlock.h>
31 
32 #define UNLIKELY(exp) __builtin_expect(!!(exp), 0)
33 
34 /* QCameraHWI_Raw class implementation goes here*/
35 /* following code implement the RDI logic of this class*/
36 
37 namespace android {
initStream(uint8_t no_cb_needed,uint8_t stream_on)38 status_t QCameraStream_Rdi::initStream(uint8_t no_cb_needed, uint8_t stream_on)
39 {
40     status_t ret = NO_ERROR;
41 
42     ALOGI(" %s : E ", __FUNCTION__);
43     mNumBuffers = PREVIEW_BUFFER_COUNT;
44     if(mHalCamCtrl->isZSLMode()) {
45         if(mNumBuffers < mHalCamCtrl->getZSLQueueDepth() + 3) {
46             mNumBuffers = mHalCamCtrl->getZSLQueueDepth() + 3;
47         }
48     }
49     ret = QCameraStream::initStream(no_cb_needed, stream_on);
50 end:
51     ALOGI(" %s : X ", __FUNCTION__);
52     return ret;
53 }
54 
getBuf(mm_camera_frame_len_offset * frame_offset_info,uint8_t num_bufs,uint8_t * initial_reg_flag,mm_camera_buf_def_t * bufs)55 int QCameraStream_Rdi::getBuf(mm_camera_frame_len_offset *frame_offset_info,
56                               uint8_t num_bufs,
57                               uint8_t *initial_reg_flag,
58                               mm_camera_buf_def_t  *bufs)
59 {
60     int ret = 0;
61     ALOGE("%s:BEGIN",__func__);
62 
63     if (num_bufs > mNumBuffers) {
64         mNumBuffers = num_bufs;
65     }
66     if ((mNumBuffers == 0) || (mNumBuffers > MM_CAMERA_MAX_NUM_FRAMES)) {
67         ALOGE("%s: Invalid number of buffers (=%d) requested!",
68              __func__, mNumBuffers);
69         return BAD_VALUE;
70     }
71 
72     memset(mRdiBuf, 0, sizeof(mRdiBuf));
73     memcpy(&mFrameOffsetInfo, frame_offset_info, sizeof(mFrameOffsetInfo));
74     ret = mHalCamCtrl->initHeapMem(&mHalCamCtrl->mRdiMemory,
75                                    mNumBuffers,
76                                    mFrameOffsetInfo.frame_len,
77                                    MSM_PMEM_MAINIMG,
78                                    &mFrameOffsetInfo,
79                                    mRdiBuf);
80     if(MM_CAMERA_OK == ret) {
81         for(int i = 0; i < num_bufs; i++) {
82             bufs[i] = mRdiBuf[i];
83             initial_reg_flag[i] = true;
84         }
85     }
86 
87     ALOGV("%s: X - ret = %d ", __func__, ret);
88     return ret;
89 }
90 
putBuf(uint8_t num_bufs,mm_camera_buf_def_t * bufs)91 int QCameraStream_Rdi::putBuf(uint8_t num_bufs, mm_camera_buf_def_t *bufs)
92 {
93     int ret = 0;
94     ALOGE(" %s : E ", __FUNCTION__);
95     ret = mHalCamCtrl->releaseHeapMem(&mHalCamCtrl->mRdiMemory);
96     ALOGI(" %s : X ",__FUNCTION__);
97     return ret;
98 }
99 
dumpFrameToFile(mm_camera_buf_def_t * newFrame)100 void QCameraStream_Rdi::dumpFrameToFile(mm_camera_buf_def_t* newFrame)
101 {
102     char buf[32];
103     int file_fd;
104     int i;
105     char *ext = "yuv";
106     int w,h,main_422;
107     static int count = 0;
108     char *name = "rdi";
109 
110     w = mHalCamCtrl->mRdiWidth;
111     h = mHalCamCtrl->mRdiHeight;
112     main_422 = 1;
113 
114     if ( newFrame != NULL) {
115         char * str;
116         snprintf(buf, sizeof(buf), "/data/%s_%d.%s", name,count,ext);
117         file_fd = open(buf, O_RDWR | O_CREAT, 0777);
118         if (file_fd < 0) {
119             ALOGE("%s: cannot open file\n", __func__);
120         } else {
121             void* y_off = newFrame->buffer + newFrame->planes[0].data_offset;
122             void* cbcr_off = newFrame->buffer + newFrame->planes[0].length;
123 
124             write(file_fd, (const void *)(y_off), newFrame->planes[0].length);
125             write(file_fd, (const void *)(cbcr_off),
126                   (newFrame->planes[1].length * newFrame->num_planes));
127             close(file_fd);
128         }
129         count++;
130     }
131 }
132 
processRdiFrame(mm_camera_super_buf_t * frame)133 status_t QCameraStream_Rdi::processRdiFrame(
134   mm_camera_super_buf_t *frame)
135 {
136     ALOGE("%s",__func__);
137     status_t err = NO_ERROR;
138     int msgType = 0;
139     camera_memory_t *data = NULL;
140 
141     if(!mActive) {
142         ALOGE("RDI Streaming Stopped. Returning callback");
143         return NO_ERROR;
144     }
145 
146     if(mHalCamCtrl==NULL) {
147         ALOGE("%s: X: HAL control object not set",__func__);
148         /*Call buf done*/
149         return BAD_VALUE;
150     }
151 
152     mHalCamCtrl->dumpFrameToFile(frame->bufs[0], HAL_DUMP_FRM_RDI);
153 
154     if (mHalCamCtrl->mDataCb != NULL) {
155       //Sending rdi callback if corresponding Msgs are enabled
156       if(mHalCamCtrl->mMsgEnabled & CAMERA_MSG_PREVIEW_FRAME) {
157           msgType |=  CAMERA_MSG_PREVIEW_FRAME;
158           data = mHalCamCtrl->mRdiMemory.camera_memory[frame->bufs[0]->buf_idx];
159       } else {
160           data = NULL;
161       }
162 
163       ALOGD("Message enabled = 0x%x", msgType);
164       if(mActive && msgType) {
165           mHalCamCtrl->mDataCb(msgType, data, 0, NULL, mHalCamCtrl->mCallbackCookie);
166       }
167       ALOGD("end of cb");
168     }
169     if (MM_CAMERA_OK != p_mm_ops->ops->qbuf(mCameraHandle, mChannelId,
170                                             frame->bufs[0])) {
171         ALOGE("%s: Failed in Preview Qbuf\n", __func__);
172         err = BAD_VALUE;
173     }
174     mHalCamCtrl->cache_ops((QCameraHalMemInfo_t *)(frame->bufs[0]->mem_info),
175                            frame->bufs[0]->buffer,
176                            ION_IOC_INV_CACHES);
177 
178     return err;
179 }
180 
181 
182 // ---------------------------------------------------------------------------
183 // QCameraStream_Rdi
184 // ---------------------------------------------------------------------------
185 
186 QCameraStream_Rdi::
QCameraStream_Rdi(uint32_t CameraHandle,uint32_t ChannelId,uint32_t Width,uint32_t Height,uint32_t Format,uint8_t NumBuffers,mm_camera_vtbl_t * mm_ops,mm_camera_img_mode imgmode,camera_mode_t mode,QCameraHardwareInterface * camCtrl)187 QCameraStream_Rdi(uint32_t CameraHandle,
188                   uint32_t ChannelId,
189                   uint32_t Width,
190                   uint32_t Height,
191                   uint32_t Format,
192                   uint8_t NumBuffers,
193                   mm_camera_vtbl_t *mm_ops,
194                   mm_camera_img_mode imgmode,
195                   camera_mode_t mode,
196                   QCameraHardwareInterface* camCtrl)
197   : QCameraStream(CameraHandle,
198                  ChannelId,
199                  Width,
200                  Height,
201                  Format,
202                  NumBuffers,
203                  mm_ops,
204                  imgmode,
205                  mode,
206                   camCtrl)
207 {
208     ALOGE("%s: E", __func__);
209     ALOGE("%s: X", __func__);
210 }
211 // ---------------------------------------------------------------------------
212 // QCameraStream_Rdi
213 // ---------------------------------------------------------------------------
214 
~QCameraStream_Rdi()215 QCameraStream_Rdi::~QCameraStream_Rdi() {
216     ALOGV("%s: E", __func__);
217     release();
218     ALOGV("%s: X", __func__);
219 
220 }
221 // ---------------------------------------------------------------------------
222 // QCameraStream_Rdi
223 // ---------------------------------------------------------------------------
release()224   void QCameraStream_Rdi::release() {
225 
226     ALOGE("%s : BEGIN",__func__);
227     streamOff(0);
228     deinitStream();
229     ALOGE("%s: END", __func__);
230   }
231 
232 // ---------------------------------------------------------------------------
233 // No code beyone this line
234 // ---------------------------------------------------------------------------
235 }; // namespace android
236