mm_qcamera_preview.c revision a1724bc599bec5b2fbe3f4a34d0eca2406ba4c5f
1/* 2Copyright (c) 2012-2013, The Linux Foundation. All rights reserved. 3 4Redistribution and use in source and binary forms, with or without 5modification, are permitted provided that the following conditions are 6met: 7 * Redistributions of source code must retain the above copyright 8 notice, this list of conditions and the following disclaimer. 9 * Redistributions in binary form must reproduce the above 10 copyright notice, this list of conditions and the following 11 disclaimer in the documentation and/or other materials provided 12 with the distribution. 13 * Neither the name of The Linux Foundation nor the names of its 14 contributors may be used to endorse or promote products derived 15 from this software without specific prior written permission. 16 17THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED 18WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 19MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT 20ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS 21BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 22CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 23SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 24BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 25WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE 26OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN 27IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28*/ 29 30#include "mm_qcamera_dbg.h" 31#include "mm_qcamera_app.h" 32 33static void mm_app_preview_notify_cb(mm_camera_super_buf_t *bufs, 34 void *user_data) 35{ 36 char file_name[64]; 37 mm_camera_buf_def_t *frame = bufs->bufs[0]; 38 mm_camera_test_obj_t *pme = (mm_camera_test_obj_t *)user_data; 39 40 CDBG("%s: BEGIN - length=%d, frame idx = %d\n", 41 __func__, frame->frame_len, frame->frame_idx); 42 snprintf(file_name, sizeof(file_name), "P_C%d", pme->cam->camera_handle); 43 mm_app_dump_frame(frame, file_name, "yuv", frame->frame_idx); 44 45 if (MM_CAMERA_OK != pme->cam->ops->qbuf(bufs->camera_handle, 46 bufs->ch_id, 47 frame)) { 48 CDBG_ERROR("%s: Failed in Preview Qbuf\n", __func__); 49 } 50 mm_app_cache_ops((mm_camera_app_meminfo_t *)frame->mem_info, 51 ION_IOC_INV_CACHES); 52 53 CDBG("%s: END\n", __func__); 54} 55 56static void mm_app_zsl_notify_cb(mm_camera_super_buf_t *bufs, 57 void *user_data) 58{ 59 int i = 0; 60 mm_camera_test_obj_t *pme = (mm_camera_test_obj_t *)user_data; 61 mm_camera_channel_t *channel = NULL; 62 mm_camera_stream_t *p_stream = NULL; 63 mm_camera_stream_t *m_stream = NULL; 64 mm_camera_buf_def_t *p_frame = NULL; 65 mm_camera_buf_def_t *m_frame = NULL; 66 67 CDBG("%s: BEGIN\n", __func__); 68 69 /* find channel */ 70 for (i = 0; i < MM_CHANNEL_TYPE_MAX; i++) { 71 if (pme->channels[i].ch_id == bufs->ch_id) { 72 channel = &pme->channels[i]; 73 break; 74 } 75 } 76 if (NULL == channel) { 77 CDBG_ERROR("%s: Wrong channel id (%d)", __func__, bufs->ch_id); 78 return; 79 } 80 81 /* find preview stream */ 82 for (i = 0; i < channel->num_streams; i++) { 83 if (channel->streams[i].s_config.stream_info->stream_type == CAM_STREAM_TYPE_PREVIEW) { 84 p_stream = &channel->streams[i]; 85 break; 86 } 87 } 88 if (NULL == p_stream) { 89 CDBG_ERROR("%s: cannot find preview stream", __func__); 90 return; 91 } 92 93 /* find snapshot stream */ 94 for (i = 0; i < channel->num_streams; i++) { 95 if (channel->streams[i].s_config.stream_info->stream_type == CAM_STREAM_TYPE_SNAPSHOT) { 96 m_stream = &channel->streams[i]; 97 break; 98 } 99 } 100 if (NULL == m_stream) { 101 CDBG_ERROR("%s: cannot find snapshot stream", __func__); 102 return; 103 } 104 105 /* find preview frame */ 106 for (i = 0; i < bufs->num_bufs; i++) { 107 if (bufs->bufs[i]->stream_id == p_stream->s_id) { 108 p_frame = bufs->bufs[i]; 109 break; 110 } 111 } 112 113 /* find snapshot frame */ 114 for (i = 0; i < bufs->num_bufs; i++) { 115 if (bufs->bufs[i]->stream_id == m_stream->s_id) { 116 m_frame = bufs->bufs[i]; 117 break; 118 } 119 } 120 121 if (!m_frame || !p_frame) { 122 CDBG_ERROR("%s: cannot find preview/snapshot frame", __func__); 123 return; 124 } 125 126 mm_app_dump_frame(p_frame, "zsl_preview", "yuv", p_frame->frame_idx); 127 mm_app_dump_frame(m_frame, "zsl_main", "yuv", m_frame->frame_idx); 128 129 if (MM_CAMERA_OK != pme->cam->ops->qbuf(bufs->camera_handle, 130 bufs->ch_id, 131 p_frame)) { 132 CDBG_ERROR("%s: Failed in preview Qbuf\n", __func__); 133 } 134 mm_app_cache_ops((mm_camera_app_meminfo_t *)p_frame->mem_info, 135 ION_IOC_INV_CACHES); 136 137 138 if (MM_CAMERA_OK != pme->cam->ops->qbuf(bufs->camera_handle, 139 bufs->ch_id, 140 m_frame)) { 141 CDBG_ERROR("%s: Failed in main Qbuf\n", __func__); 142 } 143 mm_app_cache_ops((mm_camera_app_meminfo_t *)m_frame->mem_info, 144 ION_IOC_INV_CACHES); 145 146 CDBG("%s: END\n", __func__); 147} 148 149mm_camera_stream_t * mm_app_add_preview_stream(mm_camera_test_obj_t *test_obj, 150 mm_camera_channel_t *channel, 151 mm_camera_buf_notify_t stream_cb, 152 void *userdata, 153 uint8_t num_bufs) 154{ 155 int rc = MM_CAMERA_OK; 156 mm_camera_stream_t *stream = NULL; 157 cam_capability_t *cam_cap = (cam_capability_t *)(test_obj->cap_buf.buf.buffer); 158 159 stream = mm_app_add_stream(test_obj, channel); 160 if (NULL == stream) { 161 CDBG_ERROR("%s: add stream failed\n", __func__); 162 return NULL; 163 } 164 165 stream->s_config.mem_vtbl.get_bufs = mm_app_stream_initbuf; 166 stream->s_config.mem_vtbl.put_bufs = mm_app_stream_deinitbuf; 167 stream->s_config.mem_vtbl.clean_invalidate_buf = 168 mm_app_stream_clean_invalidate_buf; 169 stream->s_config.mem_vtbl.user_data = (void *)stream; 170 stream->s_config.stream_cb = stream_cb; 171 stream->s_config.userdata = userdata; 172 stream->num_of_bufs = num_bufs; 173 174 stream->s_config.stream_info = (cam_stream_info_t *)stream->s_info_buf.buf.buffer; 175 memset(stream->s_config.stream_info, 0, sizeof(cam_stream_info_t)); 176 stream->s_config.stream_info->stream_type = CAM_STREAM_TYPE_PREVIEW; 177 stream->s_config.stream_info->streaming_mode = CAM_STREAMING_MODE_CONTINUOUS; 178 stream->s_config.stream_info->fmt = DEFAULT_PREVIEW_FORMAT; 179 stream->s_config.stream_info->dim.width = DEFAULT_PREVIEW_WIDTH; 180 stream->s_config.stream_info->dim.height = DEFAULT_PREVIEW_HEIGHT; 181 stream->s_config.padding_info = cam_cap->padding_info; 182 183 rc = mm_app_config_stream(test_obj, channel, stream, &stream->s_config); 184 if (MM_CAMERA_OK != rc) { 185 CDBG_ERROR("%s:config preview stream err=%d\n", __func__, rc); 186 return NULL; 187 } 188 189 return stream; 190} 191 192mm_camera_stream_t * mm_app_add_snapshot_stream(mm_camera_test_obj_t *test_obj, 193 mm_camera_channel_t *channel, 194 mm_camera_buf_notify_t stream_cb, 195 void *userdata, 196 uint8_t num_bufs, 197 uint8_t num_burst) 198{ 199 int rc = MM_CAMERA_OK; 200 mm_camera_stream_t *stream = NULL; 201 cam_capability_t *cam_cap = (cam_capability_t *)(test_obj->cap_buf.buf.buffer); 202 203 stream = mm_app_add_stream(test_obj, channel); 204 if (NULL == stream) { 205 CDBG_ERROR("%s: add stream failed\n", __func__); 206 return NULL; 207 } 208 209 stream->s_config.mem_vtbl.get_bufs = mm_app_stream_initbuf; 210 stream->s_config.mem_vtbl.put_bufs = mm_app_stream_deinitbuf; 211 stream->s_config.mem_vtbl.clean_invalidate_buf = 212 mm_app_stream_clean_invalidate_buf; 213 stream->s_config.mem_vtbl.user_data = (void *)stream; 214 stream->s_config.stream_cb = stream_cb; 215 stream->s_config.userdata = userdata; 216 stream->num_of_bufs = num_bufs; 217 218 stream->s_config.stream_info = (cam_stream_info_t *)stream->s_info_buf.buf.buffer; 219 memset(stream->s_config.stream_info, 0, sizeof(cam_stream_info_t)); 220 stream->s_config.stream_info->stream_type = CAM_STREAM_TYPE_SNAPSHOT; 221 if (num_burst == 0) { 222 stream->s_config.stream_info->streaming_mode = CAM_STREAMING_MODE_CONTINUOUS; 223 } else { 224 stream->s_config.stream_info->streaming_mode = CAM_STREAMING_MODE_BURST; 225 stream->s_config.stream_info->num_of_burst = num_burst; 226 } 227 stream->s_config.stream_info->fmt = DEFAULT_SNAPSHOT_FORMAT; 228 stream->s_config.stream_info->dim.width = DEFAULT_SNAPSHOT_WIDTH; 229 stream->s_config.stream_info->dim.height = DEFAULT_SNAPSHOT_HEIGHT; 230 stream->s_config.padding_info = cam_cap->padding_info; 231 232 rc = mm_app_config_stream(test_obj, channel, stream, &stream->s_config); 233 if (MM_CAMERA_OK != rc) { 234 CDBG_ERROR("%s:config preview stream err=%d\n", __func__, rc); 235 return NULL; 236 } 237 238 return stream; 239} 240 241mm_camera_channel_t * mm_app_add_preview_channel(mm_camera_test_obj_t *test_obj) 242{ 243 mm_camera_channel_t *channel = NULL; 244 mm_camera_stream_t *stream = NULL; 245 246 channel = mm_app_add_channel(test_obj, 247 MM_CHANNEL_TYPE_PREVIEW, 248 NULL, 249 NULL, 250 NULL); 251 if (NULL == channel) { 252 CDBG_ERROR("%s: add channel failed", __func__); 253 return NULL; 254 } 255 256 stream = mm_app_add_preview_stream(test_obj, 257 channel, 258 mm_app_preview_notify_cb, 259 (void *)test_obj, 260 PREVIEW_BUF_NUM); 261 if (NULL == stream) { 262 CDBG_ERROR("%s: add stream failed\n", __func__); 263 mm_app_del_channel(test_obj, channel); 264 return NULL; 265 } 266 267 return channel; 268} 269 270int mm_app_stop_and_del_channel(mm_camera_test_obj_t *test_obj, 271 mm_camera_channel_t *channel) 272{ 273 int rc = MM_CAMERA_OK; 274 mm_camera_stream_t *stream = NULL; 275 uint8_t i; 276 277 rc = mm_app_stop_channel(test_obj, channel); 278 if (MM_CAMERA_OK != rc) { 279 CDBG_ERROR("%s:Stop Preview failed rc=%d\n", __func__, rc); 280 } 281 282 for (i = 0; i < channel->num_streams; i++) { 283 stream = &channel->streams[i]; 284 rc = mm_app_del_stream(test_obj, channel, stream); 285 if (MM_CAMERA_OK != rc) { 286 CDBG_ERROR("%s:del stream(%d) failed rc=%d\n", __func__, i, rc); 287 } 288 } 289 290 rc = mm_app_del_channel(test_obj, channel); 291 if (MM_CAMERA_OK != rc) { 292 CDBG_ERROR("%s:delete channel failed rc=%d\n", __func__, rc); 293 } 294 295 return rc; 296} 297 298int mm_app_start_preview(mm_camera_test_obj_t *test_obj) 299{ 300 int rc = MM_CAMERA_OK; 301 mm_camera_channel_t *channel = NULL; 302 mm_camera_stream_t *stream = NULL; 303 uint8_t i; 304 305 channel = mm_app_add_preview_channel(test_obj); 306 if (NULL == channel) { 307 CDBG_ERROR("%s: add channel failed", __func__); 308 return -MM_CAMERA_E_GENERAL; 309 } 310 311 rc = mm_app_start_channel(test_obj, channel); 312 if (MM_CAMERA_OK != rc) { 313 CDBG_ERROR("%s:start preview failed rc=%d\n", __func__, rc); 314 for (i = 0; i < channel->num_streams; i++) { 315 stream = &channel->streams[i]; 316 mm_app_del_stream(test_obj, channel, stream); 317 } 318 mm_app_del_channel(test_obj, channel); 319 return rc; 320 } 321 322 return rc; 323} 324 325int mm_app_stop_preview(mm_camera_test_obj_t *test_obj) 326{ 327 int rc = MM_CAMERA_OK; 328 329 mm_camera_channel_t *channel = 330 mm_app_get_channel_by_type(test_obj, MM_CHANNEL_TYPE_PREVIEW); 331 332 rc = mm_app_stop_and_del_channel(test_obj, channel); 333 if (MM_CAMERA_OK != rc) { 334 CDBG_ERROR("%s:Stop Preview failed rc=%d\n", __func__, rc); 335 } 336 337 return rc; 338} 339 340int mm_app_start_preview_zsl(mm_camera_test_obj_t *test_obj) 341{ 342 int32_t rc = MM_CAMERA_OK; 343 mm_camera_channel_t *channel = NULL; 344 mm_camera_stream_t *s_preview = NULL; 345 mm_camera_stream_t *s_main = NULL; 346 mm_camera_channel_attr_t attr; 347 348 memset(&attr, 0, sizeof(mm_camera_channel_attr_t)); 349 attr.notify_mode = MM_CAMERA_SUPER_BUF_NOTIFY_BURST; 350 attr.look_back = 2; 351 attr.post_frame_skip = 0; 352 attr.water_mark = 2; 353 attr.max_unmatched_frames = 3; 354 channel = mm_app_add_channel(test_obj, 355 MM_CHANNEL_TYPE_ZSL, 356 &attr, 357 mm_app_zsl_notify_cb, 358 test_obj); 359 if (NULL == channel) { 360 CDBG_ERROR("%s: add channel failed", __func__); 361 return -MM_CAMERA_E_GENERAL; 362 } 363 364 s_preview = mm_app_add_preview_stream(test_obj, 365 channel, 366 mm_app_preview_notify_cb, 367 (void *)test_obj, 368 PREVIEW_BUF_NUM); 369 if (NULL == s_preview) { 370 CDBG_ERROR("%s: add preview stream failed\n", __func__); 371 mm_app_del_channel(test_obj, channel); 372 return rc; 373 } 374 375 s_main = mm_app_add_snapshot_stream(test_obj, 376 channel, 377 NULL, 378 NULL, 379 PREVIEW_BUF_NUM, 380 0); 381 if (NULL == s_main) { 382 CDBG_ERROR("%s: add main snapshot stream failed\n", __func__); 383 mm_app_del_stream(test_obj, channel, s_preview); 384 mm_app_del_channel(test_obj, channel); 385 return rc; 386 } 387 388 rc = mm_app_start_channel(test_obj, channel); 389 if (MM_CAMERA_OK != rc) { 390 CDBG_ERROR("%s:start zsl failed rc=%d\n", __func__, rc); 391 mm_app_del_stream(test_obj, channel, s_preview); 392 mm_app_del_stream(test_obj, channel, s_main); 393 mm_app_del_channel(test_obj, channel); 394 return rc; 395 } 396 397 return rc; 398} 399 400int mm_app_stop_preview_zsl(mm_camera_test_obj_t *test_obj) 401{ 402 int rc = MM_CAMERA_OK; 403 404 mm_camera_channel_t *channel = 405 mm_app_get_channel_by_type(test_obj, MM_CHANNEL_TYPE_ZSL); 406 407 rc = mm_app_stop_and_del_channel(test_obj, channel); 408 if (MM_CAMERA_OK != rc) { 409 CDBG_ERROR("%s:Stop Preview failed rc=%d\n", __func__, rc); 410 } 411 412 return rc; 413} 414