📄 cpia2_core.c
字号:
* * cpia2_set_high_power * *****************************************************************************/static int cpia2_set_high_power(struct camera_data *cam){ int i; for (i = 0; i <= 50; i++) { /* Read system status */ cpia2_do_command(cam,CPIA2_CMD_GET_SYSTEM_CTRL,TRANSFER_READ,0); /* If there is an error, clear it */ if(cam->params.camera_state.system_ctrl & CPIA2_SYSTEM_CONTROL_V2W_ERR) cpia2_do_command(cam, CPIA2_CMD_CLEAR_V2W_ERR, TRANSFER_WRITE, 0); /* Try to set high power mode */ cpia2_do_command(cam, CPIA2_CMD_SET_SYSTEM_CTRL, TRANSFER_WRITE, 1); /* Try to read something in VP to check if everything is awake */ cpia2_do_command(cam, CPIA2_CMD_GET_VP_SYSTEM_STATE, TRANSFER_READ, 0); if (cam->params.vp_params.system_state & CPIA2_VP_SYSTEMSTATE_HK_ALIVE) { break; } else if (i == 50) { cam->params.camera_state.power_mode = LO_POWER_MODE; ERR("Camera did not wake up\n"); return -EIO; } } DBG("System now in high power state\n"); cam->params.camera_state.power_mode = HI_POWER_MODE; return 0;}/****************************************************************************** * * cpia2_set_low_power * *****************************************************************************/int cpia2_set_low_power(struct camera_data *cam){ cam->params.camera_state.power_mode = LO_POWER_MODE; cpia2_do_command(cam, CPIA2_CMD_SET_SYSTEM_CTRL, TRANSFER_WRITE, 0); return 0;}/****************************************************************************** * * apply_vp_patch * *****************************************************************************/static int apply_vp_patch(struct camera_data *cam){ int i, j; struct cpia2_command cmd; cmd.req_mode = CAMERAACCESS_TYPE_REPEAT | CAMERAACCESS_VP; cmd.direction = TRANSFER_WRITE; for (i = 0; i < PATCH_DATA_SIZE; i++) { for (j = 0; j < patch_data[i].count; j++) { cmd.buffer.block_data[j] = patch_data[i].data[j]; } cmd.start = patch_data[i].reg; cmd.reg_count = patch_data[i].count; cpia2_send_command(cam, &cmd); } return 0;}/****************************************************************************** * * set_default_user_mode * *****************************************************************************/static int set_default_user_mode(struct camera_data *cam){ unsigned char user_mode; unsigned char frame_rate; int width = cam->params.roi.width; int height = cam->params.roi.height; switch (cam->params.version.sensor_flags) { case CPIA2_VP_SENSOR_FLAGS_404: case CPIA2_VP_SENSOR_FLAGS_407: case CPIA2_VP_SENSOR_FLAGS_409: case CPIA2_VP_SENSOR_FLAGS_410: if ((width > STV_IMAGE_QCIF_COLS) || (height > STV_IMAGE_QCIF_ROWS)) { user_mode = CPIA2_VP_USER_MODE_CIF; } else { user_mode = CPIA2_VP_USER_MODE_QCIFDS; } frame_rate = CPIA2_VP_FRAMERATE_30; break; case CPIA2_VP_SENSOR_FLAGS_500: if ((width > STV_IMAGE_CIF_COLS) || (height > STV_IMAGE_CIF_ROWS)) { user_mode = CPIA2_VP_USER_MODE_VGA; } else { user_mode = CPIA2_VP_USER_MODE_QVGADS; } if (cam->params.pnp_id.device_type == DEVICE_STV_672) frame_rate = CPIA2_VP_FRAMERATE_15; else frame_rate = CPIA2_VP_FRAMERATE_30; break; default: LOG("%s: Invalid sensor flag value 0x%0X\n",__FUNCTION__, cam->params.version.sensor_flags); return -EINVAL; } DBG("Sensor flag = 0x%0x, user mode = 0x%0x, frame rate = 0x%X\n", cam->params.version.sensor_flags, user_mode, frame_rate); cpia2_do_command(cam, CPIA2_CMD_SET_USER_MODE, TRANSFER_WRITE, user_mode); if(cam->params.vp_params.frame_rate > 0 && frame_rate > cam->params.vp_params.frame_rate) frame_rate = cam->params.vp_params.frame_rate; cpia2_set_fps(cam, frame_rate);// if (cam->params.pnp_id.device_type == DEVICE_STV_676)// cpia2_do_command(cam,// CPIA2_CMD_SET_VP_SYSTEM_CTRL,// TRANSFER_WRITE,// CPIA2_VP_SYSTEMCTRL_HK_CONTROL |// CPIA2_VP_SYSTEMCTRL_POWER_CONTROL); return 0;}/****************************************************************************** * * cpia2_match_video_size * * return the best match, where 'best' is as always * the largest that is not bigger than what is requested. *****************************************************************************/int cpia2_match_video_size(int width, int height){ if (width >= STV_IMAGE_VGA_COLS && height >= STV_IMAGE_VGA_ROWS) return VIDEOSIZE_VGA; if (width >= STV_IMAGE_CIF_COLS && height >= STV_IMAGE_CIF_ROWS) return VIDEOSIZE_CIF; if (width >= STV_IMAGE_QVGA_COLS && height >= STV_IMAGE_QVGA_ROWS) return VIDEOSIZE_QVGA; if (width >= 288 && height >= 216) return VIDEOSIZE_288_216; if (width >= 256 && height >= 192) return VIDEOSIZE_256_192; if (width >= 224 && height >= 168) return VIDEOSIZE_224_168; if (width >= 192 && height >= 144) return VIDEOSIZE_192_144; if (width >= STV_IMAGE_QCIF_COLS && height >= STV_IMAGE_QCIF_ROWS) return VIDEOSIZE_QCIF; return -1;}/****************************************************************************** * * SetVideoSize * *****************************************************************************/static int set_vw_size(struct camera_data *cam, int size){ int retval = 0; cam->params.vp_params.video_size = size; switch (size) { case VIDEOSIZE_VGA: DBG("Setting size to VGA\n"); cam->params.roi.width = STV_IMAGE_VGA_COLS; cam->params.roi.height = STV_IMAGE_VGA_ROWS; cam->vw.width = STV_IMAGE_VGA_COLS; cam->vw.height = STV_IMAGE_VGA_ROWS; break; case VIDEOSIZE_CIF: DBG("Setting size to CIF\n"); cam->params.roi.width = STV_IMAGE_CIF_COLS; cam->params.roi.height = STV_IMAGE_CIF_ROWS; cam->vw.width = STV_IMAGE_CIF_COLS; cam->vw.height = STV_IMAGE_CIF_ROWS; break; case VIDEOSIZE_QVGA: DBG("Setting size to QVGA\n"); cam->params.roi.width = STV_IMAGE_QVGA_COLS; cam->params.roi.height = STV_IMAGE_QVGA_ROWS; cam->vw.width = STV_IMAGE_QVGA_COLS; cam->vw.height = STV_IMAGE_QVGA_ROWS; break; case VIDEOSIZE_288_216: cam->params.roi.width = 288; cam->params.roi.height = 216; cam->vw.width = 288; cam->vw.height = 216; break; case VIDEOSIZE_256_192: cam->vw.width = 256; cam->vw.height = 192; cam->params.roi.width = 256; cam->params.roi.height = 192; break; case VIDEOSIZE_224_168: cam->vw.width = 224; cam->vw.height = 168; cam->params.roi.width = 224; cam->params.roi.height = 168; break; case VIDEOSIZE_192_144: cam->vw.width = 192; cam->vw.height = 144; cam->params.roi.width = 192; cam->params.roi.height = 144; break; case VIDEOSIZE_QCIF: DBG("Setting size to QCIF\n"); cam->params.roi.width = STV_IMAGE_QCIF_COLS; cam->params.roi.height = STV_IMAGE_QCIF_ROWS; cam->vw.width = STV_IMAGE_QCIF_COLS; cam->vw.height = STV_IMAGE_QCIF_ROWS; break; default: retval = -EINVAL; } return retval;}/****************************************************************************** * * configure_sensor * *****************************************************************************/static int configure_sensor(struct camera_data *cam, int req_width, int req_height){ int retval; switch (cam->params.version.sensor_flags) { case CPIA2_VP_SENSOR_FLAGS_404: case CPIA2_VP_SENSOR_FLAGS_407: case CPIA2_VP_SENSOR_FLAGS_409: case CPIA2_VP_SENSOR_FLAGS_410: retval = config_sensor_410(cam, req_width, req_height); break; case CPIA2_VP_SENSOR_FLAGS_500: retval = config_sensor_500(cam, req_width, req_height); break; default: return -EINVAL; } return retval;}/****************************************************************************** * * config_sensor_410 * *****************************************************************************/static int config_sensor_410(struct camera_data *cam, int req_width, int req_height){ struct cpia2_command cmd; int i = 0; int image_size; int image_type; int width = req_width; int height = req_height; /*** * Make sure size doesn't exceed CIF. ***/ if (width > STV_IMAGE_CIF_COLS) width = STV_IMAGE_CIF_COLS; if (height > STV_IMAGE_CIF_ROWS) height = STV_IMAGE_CIF_ROWS; image_size = cpia2_match_video_size(width, height); DBG("Config 410: width = %d, height = %d\n", width, height); DBG("Image size returned is %d\n", image_size); if (image_size >= 0) { set_vw_size(cam, image_size); width = cam->params.roi.width; height = cam->params.roi.height; DBG("After set_vw_size(), width = %d, height = %d\n", width, height); if (width <= 176 && height <= 144) { DBG("image type = VIDEOSIZE_QCIF\n"); image_type = VIDEOSIZE_QCIF; } else if (width <= 320 && height <= 240) { DBG("image type = VIDEOSIZE_QVGA\n"); image_type = VIDEOSIZE_QVGA; } else { DBG("image type = VIDEOSIZE_CIF\n"); image_type = VIDEOSIZE_CIF; } } else { ERR("ConfigSensor410 failed\n"); return -EINVAL; } cmd.req_mode = CAMERAACCESS_TYPE_RANDOM | CAMERAACCESS_VC; cmd.direction = TRANSFER_WRITE; /* VC Format */ cmd.buffer.registers[i].index = CPIA2_VC_VC_FORMAT; if (image_type == VIDEOSIZE_CIF) { cmd.buffer.registers[i++].value = (u8) (CPIA2_VC_VC_FORMAT_UFIRST | CPIA2_VC_VC_FORMAT_SHORTLINE); } else { cmd.buffer.registers[i++].value = (u8) CPIA2_VC_VC_FORMAT_UFIRST; } /* VC Clocks */ cmd.buffer.registers[i].index = CPIA2_VC_VC_CLOCKS; if (image_type == VIDEOSIZE_QCIF) { if (cam->params.pnp_id.device_type == DEVICE_STV_672) { cmd.buffer.registers[i++].value= (u8)(CPIA2_VC_VC_672_CLOCKS_CIF_DIV_BY_3 | CPIA2_VC_VC_672_CLOCKS_SCALING | CPIA2_VC_VC_CLOCKS_LOGDIV2); DBG("VC_Clocks (0xc4) should be B\n"); } else { cmd.buffer.registers[i++].value= (u8)(CPIA2_VC_VC_676_CLOCKS_CIF_DIV_BY_3 | CPIA2_VC_VC_CLOCKS_LOGDIV2); } } else { if (cam->params.pnp_id.device_type == DEVICE_STV_672) { cmd.buffer.registers[i++].value = (u8) (CPIA2_VC_VC_672_CLOCKS_CIF_DIV_BY_3 | CPIA2_VC_VC_CLOCKS_LOGDIV0); } else { cmd.buffer.registers[i++].value = (u8) (CPIA2_VC_VC_676_CLOCKS_CIF_DIV_BY_3 | CPIA2_VC_VC_676_CLOCKS_SCALING | CPIA2_VC_VC_CLOCKS_LOGDIV0); } } DBG("VC_Clocks (0xc4) = 0x%0X\n", cmd.buffer.registers[i-1].value); /* Input reqWidth from VC */ cmd.buffer.registers[i].index = CPIA2_VC_VC_IHSIZE_LO; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value = (u8) (STV_IMAGE_QCIF_COLS / 4); else cmd.buffer.registers[i++].value = (u8) (STV_IMAGE_CIF_COLS / 4); /* Timings */ cmd.buffer.registers[i].index = CPIA2_VC_VC_XLIM_HI; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value = (u8) 0; else cmd.buffer.registers[i++].value = (u8) 1; cmd.buffer.registers[i].index = CPIA2_VC_VC_XLIM_LO; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value = (u8) 208; else cmd.buffer.registers[i++].value = (u8) 160; cmd.buffer.registers[i].index = CPIA2_VC_VC_YLIM_HI; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value = (u8) 0; else cmd.buffer.registers[i++].value = (u8) 1; cmd.buffer.registers[i].index = CPIA2_VC_VC_YLIM_LO; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value = (u8) 160; else cmd.buffer.registers[i++].value = (u8) 64; /* Output Image Size */ cmd.buffer.registers[i].index = CPIA2_VC_VC_OHSIZE; cmd.buffer.registers[i++].value = cam->params.roi.width / 4; cmd.buffer.registers[i].index = CPIA2_VC_VC_OVSIZE; cmd.buffer.registers[i++].value = cam->params.roi.height / 4; /* Cropping */ cmd.buffer.registers[i].index = CPIA2_VC_VC_HCROP; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value = (u8) (((STV_IMAGE_QCIF_COLS / 4) - (width / 4)) / 2); else cmd.buffer.registers[i++].value = (u8) (((STV_IMAGE_CIF_COLS / 4) - (width / 4)) / 2); cmd.buffer.registers[i].index = CPIA2_VC_VC_VCROP; if (image_type == VIDEOSIZE_QCIF) cmd.buffer.registers[i++].value =
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -