msm-camera: Add 8MP and 1MP sensor support
Add support to mt9e013 and ov9726 sensors for v4l2 camera
architecture
Change-Id: Ie0e12bb0b8f1d80c0aa40800f5578208ca86efcb
Signed-off-by: Sandeep Kodimela <skodimela@codeaurora.org>
diff --git a/arch/arm/mach-msm/board-msm7627a-camera.c b/arch/arm/mach-msm/board-msm7627a-camera.c
index 7b075cd..ea3a36d 100644
--- a/arch/arm/mach-msm/board-msm7627a-camera.c
+++ b/arch/arm/mach-msm/board-msm7627a-camera.c
@@ -33,6 +33,39 @@
GPIO_CFG(15, 1, GPIO_CFG_OUTPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
};
+static struct gpio s5k4e1_cam_req_gpio[] = {
+ {GPIO_CAM_GP_CAMIF_RESET_N, GPIOF_DIR_OUT, "CAM_RESET"},
+};
+
+static struct msm_gpio_set_tbl s5k4e1_cam_gpio_set_tbl[] = {
+ {GPIO_CAM_GP_CAMIF_RESET_N, GPIOF_OUT_INIT_LOW, 1000},
+ {GPIO_CAM_GP_CAMIF_RESET_N, GPIOF_OUT_INIT_HIGH, 4000},
+};
+
+static struct msm_camera_gpio_conf gpio_conf_s5k4e1 = {
+ .camera_off_table = camera_off_gpio_table,
+ .camera_off_table_size = ARRAY_SIZE(camera_off_gpio_table),
+ .camera_on_table = camera_on_gpio_table,
+ .camera_on_table_size = ARRAY_SIZE(camera_on_gpio_table),
+ .cam_gpio_req_tbl = s5k4e1_cam_req_gpio,
+ .cam_gpio_req_tbl_size = ARRAY_SIZE(s5k4e1_cam_req_gpio),
+ .cam_gpio_set_tbl = s5k4e1_cam_gpio_set_tbl,
+ .cam_gpio_set_tbl_size = ARRAY_SIZE(s5k4e1_cam_gpio_set_tbl),
+ .gpio_no_mux = 1,
+};
+
+static struct msm_camera_gpio_conf gpio_conf_mt9e013 = {
+ .camera_off_table = camera_off_gpio_table,
+ .camera_on_table = camera_on_gpio_table,
+ .gpio_no_mux = 1,
+};
+
+static struct msm_camera_gpio_conf gpio_conf_ov9726 = {
+ .camera_off_table = camera_off_gpio_table,
+ .camera_on_table = camera_on_gpio_table,
+ .gpio_no_mux = 1,
+};
+
#ifdef CONFIG_MSM_CAMERA_FLASH
static struct msm_camera_sensor_flash_src msm_flash_src = {
.flash_sr_type = MSM_CAMERA_FLASH_SRC_EXT,
@@ -41,111 +74,22 @@
};
#endif
-static struct regulator_bulk_data regs_camera[] = {
- { .supply = "msme1", .min_uV = 1800000, .max_uV = 1800000 },
- { .supply = "gp2", .min_uV = 2850000, .max_uV = 2850000 },
- { .supply = "usb2", .min_uV = 1800000, .max_uV = 1800000 },
+static struct camera_vreg_t msm_cam_vreg[] = {
+ {"msme1", REG_LDO, 1800000, 1800000, 0},
+ {"gp2", REG_LDO, 2850000, 2850000, 0},
+ {"usb2", REG_LDO, 1800000, 1800000, 0},
};
-static void msm_camera_vreg_config(int vreg_en)
-{
- int rc = vreg_en ?
- regulator_bulk_enable(ARRAY_SIZE(regs_camera), regs_camera) :
- regulator_bulk_disable(ARRAY_SIZE(regs_camera), regs_camera);
-
- if (rc)
- pr_err("%s: could not %sable regulators: %d\n",
- __func__, vreg_en ? "en" : "dis", rc);
-}
-
-static int config_gpio_table(uint32_t *table, int len)
-{
- int rc = 0, i = 0;
-
- for (i = 0; i < len; i++) {
- rc = gpio_tlmm_config(table[i], GPIO_CFG_ENABLE);
- if (rc) {
- pr_err("%s not able to get gpio\n", __func__);
- for (i--; i >= 0; i--)
- gpio_tlmm_config(camera_off_gpio_table[i],
- GPIO_CFG_ENABLE);
- break;
- }
- }
- return rc;
-}
-
static struct msm_camera_sensor_info msm_camera_sensor_s5k4e1_data;
-/* TODO: static struct msm_camera_sensor_info msm_camera_sensor_ov9726_data; */
-static int config_camera_on_gpios_rear(void)
-{
- int rc = 0;
-
- if (machine_is_msm7x27a_ffa() || machine_is_msm7625a_ffa())
- msm_camera_vreg_config(1);
-
- rc = config_gpio_table(camera_on_gpio_table,
- ARRAY_SIZE(camera_on_gpio_table));
- if (rc < 0) {
- pr_err("%s: CAMSENSOR gpio table request"
- "failed\n", __func__);
- return rc;
- }
-
- return rc;
-}
-
-static void config_camera_off_gpios_rear(void)
-{
- if (machine_is_msm7x27a_ffa() || machine_is_msm7625a_ffa())
- msm_camera_vreg_config(0);
-
- config_gpio_table(camera_off_gpio_table,
- ARRAY_SIZE(camera_off_gpio_table));
-}
-
-static int config_camera_on_gpios_front(void)
-{
- int rc = 0;
-
- if (machine_is_msm7x27a_ffa() || machine_is_msm7625a_ffa())
- msm_camera_vreg_config(1);
-
- rc = config_gpio_table(camera_on_gpio_table,
- ARRAY_SIZE(camera_on_gpio_table));
- if (rc < 0) {
- pr_err("%s: CAMSENSOR gpio table request"
- "failed\n", __func__);
- return rc;
- }
-
- return rc;
-}
-
-static void config_camera_off_gpios_front(void)
-{
- if (machine_is_msm7x27a_ffa() || machine_is_msm7625a_ffa())
- msm_camera_vreg_config(0);
-
- config_gpio_table(camera_off_gpio_table,
- ARRAY_SIZE(camera_off_gpio_table));
-}
struct msm_camera_device_platform_data msm_camera_device_data_csi1 = {
- .camera_gpio_on = config_camera_on_gpios_rear,
- .camera_gpio_off = config_camera_off_gpios_rear,
- .ioclk.mclk_clk_rate = 24000000,
- .ioclk.vfe_clk_rate = 192000000,
.csid_core = 1,
.is_csic = 1,
};
struct msm_camera_device_platform_data msm_camera_device_data_csi0 = {
- .camera_gpio_on = config_camera_on_gpios_front,
- .camera_gpio_off = config_camera_off_gpios_front,
- .ioclk.mclk_clk_rate = 24000000,
- .ioclk.vfe_clk_rate = 192000000,
.csid_core = 0,
+ .is_csic = 1,
};
#ifdef CONFIG_DW9712_ACT
@@ -169,10 +113,9 @@
static struct msm_camera_sensor_platform_info sensor_board_info_s5k4e1 = {
.mount_angle = 90,
- .sensor_reset = GPIO_CAM_GP_CAMIF_RESET_N,
- .sensor_pwd = 85,
- .vcm_pwd = GPIO_CAM_GP_CAM_PWDN,
- .vcm_enable = 1,
+ .cam_vreg = msm_cam_vreg,
+ .num_vreg = ARRAY_SIZE(msm_cam_vreg),
+ .gpio_conf = &gpio_conf_s5k4e1,
};
static struct msm_camera_sensor_info msm_camera_sensor_s5k4e1_data = {
@@ -198,10 +141,9 @@
static struct msm_camera_sensor_platform_info sensor_board_info_mt9e013 = {
.mount_angle = 90,
- .sensor_reset = 0,
- .sensor_pwd = 85,
- .vcm_pwd = 1,
- .vcm_enable = 0,
+ .cam_vreg = msm_cam_vreg,
+ .num_vreg = ARRAY_SIZE(msm_cam_vreg),
+ .gpio_conf = &gpio_conf_mt9e013,
};
static struct msm_camera_sensor_info msm_camera_sensor_mt9e013_data = {
@@ -256,10 +198,9 @@
static struct msm_camera_sensor_platform_info sensor_board_info_ov9726 = {
.mount_angle = 90,
- .sensor_reset = GPIO_CAM_GP_CAM1MP_XCLR,
- .sensor_pwd = 85,
- .vcm_pwd = 1,
- .vcm_enable = 0,
+ .cam_vreg = msm_cam_vreg,
+ .num_vreg = ARRAY_SIZE(msm_cam_vreg),
+ .gpio_conf = &gpio_conf_ov9726,
};
static struct msm_camera_sensor_info msm_camera_sensor_ov9726_data = {
@@ -276,6 +217,15 @@
static void __init msm7x27a_init_cam(void)
{
+ if (!(machine_is_msm7x27a_ffa() || machine_is_msm7625a_ffa()
+ || machine_is_msm7627a_qrd1())) {
+ sensor_board_info_s5k4e1.cam_vreg = NULL;
+ sensor_board_info_s5k4e1.num_vreg = 0;
+ sensor_board_info_mt9e013.cam_vreg = NULL;
+ sensor_board_info_mt9e013.num_vreg = 0;
+ sensor_board_info_ov9726.cam_vreg = NULL;
+ sensor_board_info_ov9726.num_vreg = 0;
+ }
platform_device_register(&msm7x27a_device_csic0);
platform_device_register(&msm7x27a_device_csic1);
platform_device_register(&msm7x27a_device_clkctl);
@@ -939,6 +889,7 @@
ARRAY_SIZE(cam_exp_i2c_info));
}
+#ifndef CONFIG_MSM_CAMERA_V4L2
#define LCD_CAMERA_LDO_2V8 35 /* SKU1&SKU3 2.8V LDO */
#define SKU3_LCD_CAMERA_LDO_1V8 40 /* SKU3 1.8V LDO */
@@ -1033,10 +984,11 @@
return rc;
}
EXPORT_SYMBOL(lcd_camera_power_onoff);
-
+#endif
void __init msm7627a_camera_init(void)
{
+#ifndef CONFIG_MSM_CAMERA_V4L2
int rc;
pr_debug("msm7627a_camera_init Entered\n");
@@ -1044,7 +996,6 @@
if (machine_is_msm7627a_evb() || machine_is_msm8625_evb())
lcd_camera_power_init();
-#ifndef CONFIG_MSM_CAMERA_V4L2
if (machine_is_msm7627a_qrd1()) {
qrd1_camera_gpio_cfg();
platform_add_devices(camera_devices_qrd,
@@ -1062,6 +1013,7 @@
if (!machine_is_msm7627a_qrd1() || !machine_is_msm7627a_evb()
|| !machine_is_msm8625_evb())
register_i2c_devices();
+#ifndef CONFIG_MSM_CAMERA_V4L2
rc = regulator_bulk_get(NULL, ARRAY_SIZE(regs_camera), regs_camera);
if (rc) {
@@ -1075,6 +1027,7 @@
pr_err("%s: could not set voltages: %d\n", __func__, rc);
return;
}
+#endif
#if defined(CONFIG_MSM_CAMERA_V4L2)
msm7x27a_init_cam();
@@ -1091,6 +1044,7 @@
ARRAY_SIZE(i2c_camera_devices_evb));
} else
#endif
+ pr_debug("i2c_register_board_info\n");
i2c_register_board_info(MSM_GSBI0_QUP_I2C_BUS_ID,
i2c_camera_devices,
ARRAY_SIZE(i2c_camera_devices));
diff --git a/arch/arm/mach-msm/clock-pcom-lookup.c b/arch/arm/mach-msm/clock-pcom-lookup.c
index c20b7e4..f43a468 100644
--- a/arch/arm/mach-msm/clock-pcom-lookup.c
+++ b/arch/arm/mach-msm/clock-pcom-lookup.c
@@ -317,6 +317,9 @@
CLK_LOOKUP("ahb_m_clk", ahb_m_clk.c, NULL),
CLK_LOOKUP("ahb_s_clk", ahb_s_clk.c, NULL),
CLK_LOOKUP("cam_m_clk", cam_m_clk.c, NULL),
+ CLK_LOOKUP("cam_clk", cam_m_clk.c, "0-0036"),
+ CLK_LOOKUP("cam_clk", cam_m_clk.c, "0-001b"),
+ CLK_LOOKUP("cam_clk", cam_m_clk.c, "0-0010"),
CLK_LOOKUP("csi_clk", csi0_clk.c, "msm_camera_ov9726.0"),
CLK_LOOKUP("csi_pclk", csi0_p_clk.c, "msm_camera_ov9726.0"),
CLK_LOOKUP("csi_vfe_clk", csi0_vfe_clk.c, "msm_camera_ov9726.0"),
diff --git a/arch/arm/mach-msm/include/mach/board.h b/arch/arm/mach-msm/include/mach/board.h
index a87a759..7fa4a07 100644
--- a/arch/arm/mach-msm/include/mach/board.h
+++ b/arch/arm/mach-msm/include/mach/board.h
@@ -200,6 +200,11 @@
uint8_t cam_gpio_req_tbl_size;
struct msm_gpio_set_tbl *cam_gpio_set_tbl;
uint8_t cam_gpio_set_tbl_size;
+ uint32_t gpio_no_mux;
+ uint32_t *camera_off_table;
+ uint8_t camera_off_table_size;
+ uint32_t *camera_on_table;
+ uint8_t camera_on_table_size;
};
enum msm_camera_i2c_mux_mode {
diff --git a/drivers/media/video/msm/Makefile b/drivers/media/video/msm/Makefile
index 8703669..67cd62e 100644
--- a/drivers/media/video/msm/Makefile
+++ b/drivers/media/video/msm/Makefile
@@ -44,7 +44,6 @@
obj-$(CONFIG_QS_S5K4E1) += qs_s5k4e1.o qs_s5k4e1_reg.o
obj-$(CONFIG_VB6801) += vb6801.o
obj-$(CONFIG_IMX072) += imx072.o imx072_reg.o
-obj-$(CONFIG_WEBCAM_OV9726) += ov9726.o ov9726_reg.o
obj-$(CONFIG_OV5647) += ov5647.o ov5647_reg.o
obj-$(CONFIG_WEBCAM_OV7692) += ov7692.o
obj-$(CONFIG_WEBCAM_OV7692_QRD) += ov7692_qrd.o
diff --git a/drivers/media/video/msm/actuators/dw9712_act.c b/drivers/media/video/msm/actuators/dw9712_act.c
index 562290f..546cffa 100644
--- a/drivers/media/video/msm/actuators/dw9712_act.c
+++ b/drivers/media/video/msm/actuators/dw9712_act.c
@@ -101,9 +101,9 @@
/* Determine sign direction */
if (dir == MOVE_NEAR)
- sign_dir = 1;
+ sign_dir = 16;
else if (dir == MOVE_FAR)
- sign_dir = -1;
+ sign_dir = -16;
else {
pr_err("Illegal focus direction\n");
rc = -EINVAL;
diff --git a/drivers/media/video/msm/io/msm_io_util.c b/drivers/media/video/msm/io/msm_io_util.c
index 207f8be..a04d6fd 100644
--- a/drivers/media/video/msm/io/msm_io_util.c
+++ b/drivers/media/video/msm/io/msm_io_util.c
@@ -95,32 +95,33 @@
curr_vreg->reg_name);
if (IS_ERR(reg_ptr[i])) {
pr_err("%s: %s get failed\n",
- __func__,
- curr_vreg->reg_name);
+ __func__,
+ curr_vreg->reg_name);
reg_ptr[i] = NULL;
goto vreg_get_fail;
}
if (curr_vreg->type == REG_LDO) {
rc = regulator_set_voltage(
- reg_ptr[i],
- curr_vreg->min_voltage,
- curr_vreg->max_voltage);
+ reg_ptr[i],
+ curr_vreg->min_voltage,
+ curr_vreg->max_voltage);
if (rc < 0) {
- pr_err(
- "%s: %s set voltage failed\n",
- __func__,
- curr_vreg->reg_name);
+ pr_err("%s: %s set voltage failed\n",
+ __func__,
+ curr_vreg->reg_name);
goto vreg_set_voltage_fail;
}
- rc = regulator_set_optimum_mode(
- reg_ptr[i],
- curr_vreg->op_mode);
- if (rc < 0) {
- pr_err(
- "%s: %s set optimum mode failed\n",
- __func__,
- curr_vreg->reg_name);
- goto vreg_set_opt_mode_fail;
+ if (curr_vreg->op_mode) {
+ rc = regulator_set_optimum_mode(
+ reg_ptr[i],
+ curr_vreg->op_mode);
+ if (rc < 0) {
+ pr_err("%s: %s set optimum"
+ "mode failed\n",
+ __func__,
+ curr_vreg->reg_name);
+ goto vreg_set_opt_mode_fail;
+ }
}
}
}
@@ -129,11 +130,12 @@
curr_vreg = &cam_vreg[i];
if (reg_ptr[i]) {
if (curr_vreg->type == REG_LDO) {
- regulator_set_optimum_mode(
- reg_ptr[i], 0);
+ if (curr_vreg->op_mode)
+ regulator_set_optimum_mode(
+ reg_ptr[i], 0);
regulator_set_voltage(
- reg_ptr[i],
- 0, curr_vreg->max_voltage);
+ reg_ptr[i], 0, curr_vreg->
+ max_voltage);
}
regulator_put(reg_ptr[i]);
reg_ptr[i] = NULL;
@@ -171,13 +173,13 @@
for (i = 0; i < num_vreg; i++) {
if (IS_ERR(reg_ptr[i])) {
pr_err("%s: %s null regulator\n",
- __func__, cam_vreg[i].reg_name);
+ __func__, cam_vreg[i].reg_name);
goto disable_vreg;
}
rc = regulator_enable(reg_ptr[i]);
if (rc < 0) {
pr_err("%s: %s enable failed\n",
- __func__, cam_vreg[i].reg_name);
+ __func__, cam_vreg[i].reg_name);
goto disable_vreg;
}
}
@@ -194,6 +196,30 @@
return rc;
}
+static int config_gpio_table(struct msm_camera_gpio_conf *gpio)
+{
+ int rc = 0, i = 0;
+ uint32_t *table_on;
+ uint32_t *table_off;
+ uint32_t len;
+
+ table_on = gpio->camera_on_table;
+ table_off = gpio->camera_off_table;
+ len = gpio->camera_on_table_size;
+
+ for (i = 0; i < len; i++) {
+ rc = gpio_tlmm_config(table_on[i], GPIO_CFG_ENABLE);
+ if (rc) {
+ pr_err("%s not able to get gpio\n", __func__);
+ for (i--; i >= 0; i--)
+ gpio_tlmm_config(table_off[i],
+ GPIO_CFG_ENABLE);
+ break;
+ }
+ }
+ return rc;
+}
+
int msm_camera_request_gpio_table(struct msm_camera_sensor_info *sinfo,
int gpio_en)
{
@@ -201,38 +227,49 @@
struct msm_camera_gpio_conf *gpio_conf =
sinfo->sensor_platform_info->gpio_conf;
- if (gpio_conf->cam_gpio_req_tbl == NULL ||
- gpio_conf->cam_gpio_common_tbl == NULL) {
- pr_err("%s: NULL camera gpio table\n", __func__);
- return -EFAULT;
+ if (!gpio_conf->gpio_no_mux) {
+ if (gpio_conf->cam_gpio_req_tbl == NULL ||
+ gpio_conf->cam_gpio_common_tbl == NULL) {
+ pr_err("%s: NULL camera gpio table\n", __func__);
+ return -EFAULT;
+ }
}
+ if (gpio_conf->gpio_no_mux)
+ config_gpio_table(gpio_conf);
if (gpio_en) {
- if (gpio_conf->cam_gpiomux_conf_tbl != NULL) {
- msm_gpiomux_install(
- (struct msm_gpiomux_config *)gpio_conf->
- cam_gpiomux_conf_tbl,
- gpio_conf->cam_gpiomux_conf_tbl_size);
- }
- rc = gpio_request_array(gpio_conf->cam_gpio_common_tbl,
+ if (!gpio_conf->gpio_no_mux) {
+ if (gpio_conf->cam_gpiomux_conf_tbl != NULL) {
+ msm_gpiomux_install(
+ (struct msm_gpiomux_config *)
+ gpio_conf->cam_gpiomux_conf_tbl,
+ gpio_conf->cam_gpiomux_conf_tbl_size);
+ }
+ rc = gpio_request_array(gpio_conf->cam_gpio_common_tbl,
gpio_conf->cam_gpio_common_tbl_size);
- if (rc < 0) {
- pr_err("%s common gpio request failed\n", __func__);
- return rc;
+ if (rc < 0) {
+ pr_err("%s common gpio request failed\n"
+ , __func__);
+ return rc;
+ }
}
- rc = gpio_request_array(gpio_conf->cam_gpio_req_tbl,
+ if (gpio_conf->cam_gpio_req_tbl_size) {
+ rc = gpio_request_array(gpio_conf->cam_gpio_req_tbl,
gpio_conf->cam_gpio_req_tbl_size);
- if (rc < 0) {
- pr_err("%s camera gpio request failed\n", __func__);
- gpio_free_array(gpio_conf->cam_gpio_common_tbl,
- gpio_conf->cam_gpio_common_tbl_size);
- return rc;
+ if (rc < 0) {
+ pr_err("%s camera gpio"
+ "request failed\n", __func__);
+ gpio_free_array(gpio_conf->cam_gpio_common_tbl,
+ gpio_conf->cam_gpio_common_tbl_size);
+ return rc;
+ }
}
} else {
gpio_free_array(gpio_conf->cam_gpio_req_tbl,
gpio_conf->cam_gpio_req_tbl_size);
- gpio_free_array(gpio_conf->cam_gpio_common_tbl,
- gpio_conf->cam_gpio_common_tbl_size);
+ if (!gpio_conf->gpio_no_mux)
+ gpio_free_array(gpio_conf->cam_gpio_common_tbl,
+ gpio_conf->cam_gpio_common_tbl_size);
}
return rc;
}
@@ -252,7 +289,7 @@
usleep_range(gpio_conf->cam_gpio_set_tbl[i].delay,
gpio_conf->cam_gpio_set_tbl[i].delay + 1000);
}
- } else {
+ } else if (!gpio_conf->gpio_no_mux) {
for (i = gpio_conf->cam_gpio_set_tbl_size - 1; i >= 0; i--) {
if (gpio_conf->cam_gpio_set_tbl[i].flags)
gpio_set_value_cansleep(
diff --git a/drivers/media/video/msm/msm_io_7x27a_v4l2.c b/drivers/media/video/msm/msm_io_7x27a_v4l2.c
index bee9f49..63547c8 100644
--- a/drivers/media/video/msm/msm_io_7x27a_v4l2.c
+++ b/drivers/media/video/msm/msm_io_7x27a_v4l2.c
@@ -97,33 +97,6 @@
clk_set_rate(clk, rate);
}
-int msm_sensor_probe_on(struct device *dev)
-{
- int rc = 0;
- struct msm_camera_sensor_info *sinfo = dev->platform_data;
- struct msm_camera_device_platform_data *camdev = sinfo->pdata;
- camio_clk = camdev->ioclk;
-
- rc = camdev->camera_gpio_on();
- if (rc < 0)
- return rc;
-
- rc = msm_camio_clk_enable(CAMIO_CAM_MCLK_CLK);
- if (rc < 0)
- camdev->camera_gpio_off();
-
- return rc;
-}
-
-int msm_sensor_probe_off(struct device *dev)
-{
- struct msm_camera_sensor_info *sinfo = dev->platform_data;
- struct msm_camera_device_platform_data *camdev = sinfo->pdata;
-
- camdev->camera_gpio_off();
- return msm_camio_clk_disable(CAMIO_CAM_MCLK_CLK);
-}
-
void msm_camio_vfe_blk_reset(void)
{
uint32_t val;
@@ -152,28 +125,6 @@
usleep_range(10000, 11000);
}
-int msm_camio_probe_on(struct platform_device *pdev)
-{
- int rc = 0;
- const struct msm_camera_sensor_info *sinfo = pdev->dev.platform_data;
- struct msm_camera_device_platform_data *camdev = sinfo->pdata;
- camio_clk = camdev->ioclk;
-
- rc = camdev->camera_gpio_on();
- if (rc < 0)
- return rc;
- return msm_camio_clk_enable(CAMIO_CAM_MCLK_CLK);
-}
-
-int msm_camio_probe_off(struct platform_device *pdev)
-{
- const struct msm_camera_sensor_info *sinfo = pdev->dev.platform_data;
- struct msm_camera_device_platform_data *camdev = sinfo->pdata;
-
- camdev->camera_gpio_off();
- return msm_camio_clk_disable(CAMIO_CAM_MCLK_CLK);
-}
-
void msm_camio_set_perf_lvl(enum msm_bus_perf_setting perf_setting)
{
switch (perf_setting) {
diff --git a/drivers/media/video/msm/msm_isp.c b/drivers/media/video/msm/msm_isp.c
index a0ac70d..3e2ddee 100644
--- a/drivers/media/video/msm/msm_isp.c
+++ b/drivers/media/video/msm/msm_isp.c
@@ -127,6 +127,10 @@
case VFE_OUTPUTS_JPEG_AND_THUMB:
image_mode = MSM_V4L2_EXT_CAPTURE_MODE_THUMBNAIL;
break;
+ case VFE_OUTPUTS_PREVIEW:
+ case VFE_OUTPUTS_VIDEO:
+ image_mode = MSM_V4L2_EXT_CAPTURE_MODE_PREVIEW;
+ break;
default:
image_mode = -1;
break;
@@ -402,6 +406,8 @@
stats.cs.buff = stats.buffer;
stats.cs.fd = stats.fd;
break;
+ case MSG_ID_STATS_AWB_AEC:
+ break;
default:
pr_err("%s: Invalid msg type", __func__);
break;
@@ -722,6 +728,7 @@
case CMD_AXI_CFG_ZSL_ALL_CHNLS:
case CMD_RAW_PICT_AXI_CFG:
case CMD_AXI_CFG_PRIM:
+ case CMD_AXI_CFG_SEC:
case CMD_AXI_CFG_PRIM_ALL_CHNLS:
case CMD_AXI_CFG_PRIM|CMD_AXI_CFG_SEC:
case CMD_AXI_CFG_PRIM|CMD_AXI_CFG_SEC_ALL_CHNLS:
diff --git a/drivers/media/video/msm/msm_vfe7x27a_v4l2.c b/drivers/media/video/msm/msm_vfe7x27a_v4l2.c
index 638c51d..07a4c89 100644
--- a/drivers/media/video/msm/msm_vfe7x27a_v4l2.c
+++ b/drivers/media/video/msm/msm_vfe7x27a_v4l2.c
@@ -327,6 +327,9 @@
{VFE_CMD_SCALE_OUTPUT2_CONFIG, VFE_SCALE_OUTPUT2_CONFIG,
QDSP_SCALEQUEUE, "VFE_CMD_SCALE_OUTPUT2_CONFIG",
"VFE_SCALE_OUTPUT2_CONFIG"},
+ {VFE_CMD_CAPTURE_RAW, VFE_START, QDSP_CMDQUEUE,
+ "VFE_CMD_CAPTURE_RAW", "VFE_START"},
+ {VFE_CMD_RECONFIG_VFE, VFE_MAX, VFE_MAX},
};
@@ -400,9 +403,9 @@
unsigned char buf[256];
struct msm_free_buf *free_buf = NULL;
struct vfe_outputack fack;
+ int i;
CDBG("%s:id=%d\n", __func__, id);
-
if (id != VFE_ADSP_EVENT) {
data = kzalloc(len, GFP_KERNEL);
if (!data) {
@@ -434,8 +437,9 @@
cbcr_phy = outch->ping.ch_paddr[1];
CDBG("MSG_OUTPUT_S: %x %x\n",
(unsigned int)y_phy, (unsigned int)cbcr_phy);
- vfe_send_outmsg(&vfe2x_ctrl->subdev, MSG_ID_OUTPUT_S,
- y_phy, cbcr_phy);
+ vfe_send_outmsg(&vfe2x_ctrl->subdev,
+ MSG_ID_OUTPUT_PRIMARY,
+ y_phy, cbcr_phy);
break;
case MSG_OUTPUT_T:
outch = &vfe2x_ctrl->thumb;
@@ -443,7 +447,8 @@
cbcr_phy = outch->ping.ch_paddr[1];
CDBG("MSG_OUTPUT_T: %x %x\n",
(unsigned int)y_phy, (unsigned int)cbcr_phy);
- vfe_send_outmsg(&vfe2x_ctrl->subdev, MSG_ID_OUTPUT_T,
+ vfe_send_outmsg(&vfe2x_ctrl->subdev,
+ MSG_ID_OUTPUT_SECONDARY,
y_phy, cbcr_phy);
break;
case MSG_OUTPUT1:
@@ -454,7 +459,7 @@
} else {
free_buf = vfe2x_check_free_buffer(
VFE_MSG_OUTPUT_IRQ,
- VFE_MSG_OUTPUT_P);
+ VFE_MSG_OUTPUT_PRIMARY);
CDBG("free_buf = %x\n", (unsigned int) free_buf);
if (free_buf) {
fack.header = VFE_OUTPUT2_ACK;
@@ -489,7 +494,22 @@
CDBG("vfe_7x_convert, y_phy = 0x%x, cbcr_phy = 0x%x\n",
y_phy, cbcr_phy);
-
+ if (free_buf) {
+ for (i = 0; i < 3; i++) {
+ if (vfe2x_ctrl->free_buf.buf[i].
+ ch_paddr[0] == y_phy) {
+ vfe2x_ctrl->free_buf.
+ buf[i].ch_paddr[0] =
+ free_buf->ch_paddr[0];
+ vfe2x_ctrl->free_buf.
+ buf[i].ch_paddr[1] =
+ free_buf->ch_paddr[1];
+ break;
+ }
+ }
+ if (i == 3)
+ CDBG("Address doesnt match\n");
+ }
memcpy(((struct vfe_frame_extra *)extdata),
&((struct vfe_endframe *)data)->extra,
sizeof(struct vfe_frame_extra));
@@ -497,8 +517,8 @@
vfe2x_ctrl->vfeFrameId =
((struct vfe_frame_extra *)extdata)->frame_id;
vfe_send_outmsg(&vfe2x_ctrl->subdev,
- MSG_ID_OUTPUT_P,
- y_phy, cbcr_phy);
+ MSG_ID_OUTPUT_PRIMARY,
+ y_phy, cbcr_phy);
break;
case MSG_RESET_ACK:
case MSG_START_ACK:
@@ -509,11 +529,55 @@
vfe2x_send_isp_msg(vfe2x_ctrl, msgs_map[id].isp_id);
if (id == MSG_START_ACK)
vfe2x_ctrl->vfe_started = 1;
+ if (id == MSG_VFE_ERROR) {
+ uint16_t *ptr;
+ struct vfe_error_msg *VFE_ErrorMessageBuffer
+ = data;
+ ptr = data;
+ CDBG("Error: %x %x\n", ptr[0], ptr[1]);
+ CDBG("CAMIF_Error = %d\n",
+ VFE_ErrorMessageBuffer->camif_error);
+ CDBG("output1YBusOverflow = %d\n",
+ VFE_ErrorMessageBuffer->
+ output1ybusoverflow);
+ CDBG("output1CbCrBusOverflow = %d\n",
+ VFE_ErrorMessageBuffer->
+ output1cbcrbusoverflow);
+ CDBG("output2YBusOverflow = %d\n",
+ VFE_ErrorMessageBuffer->
+ output2ybusoverflow);
+ CDBG("output2CbCrBusOverflow = %d\n",
+ VFE_ErrorMessageBuffer->
+ output2cbcrbusoverflow);
+ CDBG("autofocusStatBusOverflow = %d\n",
+ VFE_ErrorMessageBuffer->
+ autofocusstatbusoverflow);
+ CDBG("WB_EXPStatBusOverflow = %d\n",
+ VFE_ErrorMessageBuffer->
+ wb_expstatbusoverflow);
+ CDBG("AXIError = %d\n",
+ VFE_ErrorMessageBuffer->
+ axierror);
+ CDBG("CAMIF_Staus = %d\n",
+ VFE_ErrorMessageBuffer->
+ camif_staus);
+ CDBG("pixel_count = %d\n",
+ VFE_ErrorMessageBuffer->
+ pixel_count);
+ CDBG("line_count = %d\n",
+ VFE_ErrorMessageBuffer->
+ line_count);
+ }
break;
case MSG_SOF:
vfe2x_ctrl->vfeFrameId++;
if (vfe2x_ctrl->vfeFrameId == 0)
vfe2x_ctrl->vfeFrameId = 1; /* wrapped back */
+ if ((op_mode & SNAPSHOT_MASK_MODE) && !raw_mode) {
+ pr_err("Ignore SOF for snapshot\n");
+ kfree(data);
+ return;
+ }
vfe2x_send_isp_msg(vfe2x_ctrl, MSG_ID_SOF_ACK);
if (raw_mode)
vfe2x_send_isp_msg(vfe2x_ctrl,
@@ -584,9 +648,13 @@
unsigned long *bptr;
int cnt;
int rc = 0;
+ int o_mode = 0;
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ o_mode = SNAPSHOT_MASK_MODE;
- if (mode == OUTPUT_1) {
+ if (mode == OUTPUT_SEC) {
+ /* Thumbnail */
ao->output1buffer1_y_phy = ad->ping.ch_paddr[0];
ao->output1buffer1_cbcr_phy = ad->ping.ch_paddr[1];
ao->output1buffer2_y_phy = ad->pong.ch_paddr[0];
@@ -598,9 +666,8 @@
*bptr = ad->pong.ch_paddr[1];
bptr++;
}
- }
-
- if (mode == OUTPUT_2) {
+ } else if (mode == OUTPUT_PRIM && o_mode != SNAPSHOT_MASK_MODE) {
+ /* Preview */
ao->output2buffer1_y_phy = ad->ping.ch_paddr[0];
ao->output2buffer1_cbcr_phy = ad->ping.ch_paddr[1];
ao->output2buffer2_y_phy = ad->pong.ch_paddr[0];
@@ -614,9 +681,30 @@
*bptr = ad->pong.ch_paddr[1];
bptr++;
}
- }
-
- if (mode == OUTPUT_1_AND_2) {
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer1_y_phy,
+ (unsigned int)ao->output2buffer1_cbcr_phy);
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer2_y_phy,
+ (unsigned int)ao->output2buffer2_cbcr_phy);
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer3_y_phy,
+ (unsigned int)ao->output2buffer3_cbcr_phy);
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer4_y_phy,
+ (unsigned int)ao->output2buffer4_cbcr_phy);
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer5_y_phy,
+ (unsigned int)ao->output2buffer5_cbcr_phy);
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer6_y_phy,
+ (unsigned int)ao->output2buffer6_cbcr_phy);
+ CDBG("%x %x\n", (unsigned int)ao->output2buffer7_y_phy,
+ (unsigned int)ao->output2buffer7_cbcr_phy);
+ vfe2x_ctrl->free_buf.buf[0].ch_paddr[0] = ad->ping.ch_paddr[0];
+ vfe2x_ctrl->free_buf.buf[0].ch_paddr[1] = ad->ping.ch_paddr[1];
+ vfe2x_ctrl->free_buf.buf[1].ch_paddr[0] = ad->pong.ch_paddr[0];
+ vfe2x_ctrl->free_buf.buf[1].ch_paddr[1] = ad->pong.ch_paddr[1];
+ vfe2x_ctrl->free_buf.buf[2].ch_paddr[0] =
+ ad->free_buf.ch_paddr[0];
+ vfe2x_ctrl->free_buf.buf[2].ch_paddr[1] =
+ ad->free_buf.ch_paddr[1];
+ } else if (mode == OUTPUT_PRIM && o_mode == SNAPSHOT_MASK_MODE) {
+ vfe2x_ctrl->reconfig_vfe = 0;
if (raw_mode) {
ao->output2buffer1_y_phy = ad->ping.ch_paddr[0];
ao->output2buffer1_cbcr_phy = ad->ping.ch_paddr[0];
@@ -632,7 +720,7 @@
for (cnt = 0; cnt < 6; cnt++) {
*bptr = ad->pong.ch_paddr[0];
bptr++;
- *bptr = ad->pong.ch_paddr[0];
+ *bptr = ad->pong.ch_paddr[1];
bptr++;
}
}
@@ -664,12 +752,12 @@
vfe2x_subdev_notify(id, path);
if (op_mode & SNAPSHOT_MASK_MODE) {
- if (path == VFE_MSG_OUTPUT_S)
+ if (path == VFE_MSG_OUTPUT_PRIMARY)
outch = &vfe2x_ctrl->snap;
- else if (path == VFE_MSG_OUTPUT_T)
+ else if (path == VFE_MSG_OUTPUT_SECONDARY)
outch = &vfe2x_ctrl->thumb;
} else {
- if (path == VFE_MSG_OUTPUT_P)
+ if (path == VFE_MSG_OUTPUT_PRIMARY)
outch = &vfe2x_ctrl->prev;
}
if (outch->free_buf.ch_paddr[0])
@@ -684,15 +772,14 @@
int rc = 0;
vfe2x_subdev_notify(id, path);
-
CDBG("Opmode = %d\n", op_mode);
if (op_mode & SNAPSHOT_MASK_MODE) {
- if (path == VFE_MSG_OUTPUT_S)
+ if (path == VFE_MSG_OUTPUT_PRIMARY)
outch = &vfe2x_ctrl->snap;
- else if (path == VFE_MSG_OUTPUT_T)
+ else if (path == VFE_MSG_OUTPUT_SECONDARY)
outch = &vfe2x_ctrl->thumb;
} else {
- if (path == VFE_MSG_OUTPUT_P)
+ if (path == VFE_MSG_OUTPUT_PRIMARY)
outch = &vfe2x_ctrl->prev;
}
if (outch->ping.ch_paddr[0] && outch->pong.ch_paddr[0]) {
@@ -711,13 +798,14 @@
struct buf_info *ch = NULL;
CDBG("path = %d op_mode = %d\n", path, op_mode);
+ /* TODO: Remove Mode specific stuff */
if (op_mode & SNAPSHOT_MASK_MODE) {
- if (path == VFE_MSG_OUTPUT_T)
+ if (path == VFE_MSG_OUTPUT_SECONDARY)
ch = &vfe2x_ctrl->thumb;
- else if (path == VFE_MSG_OUTPUT_S)
+ else if (path == VFE_MSG_OUTPUT_PRIMARY)
ch = &vfe2x_ctrl->snap;
} else {
- if (path == VFE_MSG_OUTPUT_P)
+ if (path == VFE_MSG_OUTPUT_PRIMARY)
ch = &vfe2x_ctrl->prev;
}
@@ -777,11 +865,11 @@
if (op_mode & SNAPSHOT_MASK_MODE) {
free_buf = vfe2x_check_free_buffer(
VFE_MSG_OUTPUT_IRQ,
- VFE_MSG_OUTPUT_T);
+ VFE_MSG_OUTPUT_SECONDARY);
} else {
free_buf = vfe2x_check_free_buffer(
VFE_MSG_OUTPUT_IRQ,
- VFE_MSG_OUTPUT_P);
+ VFE_MSG_OUTPUT_PRIMARY);
if (free_buf) {
fack.header = VFE_OUTPUT2_ACK;
@@ -875,6 +963,7 @@
break;
case CMD_STATS_AF_ENABLE:
case CMD_STATS_AF_AXI_CFG: {
+ CDBG("CMD_STATS_AF_ENABLE CMD_STATS_AF_AXI_CFG\n");
axid = data;
if (!axid) {
rc = -EFAULT;
@@ -908,6 +997,7 @@
goto config_failure;
}
*(uint32_t *)sfcfg = header;
+ CDBG("Number of buffers = %d\n", axid->bufnum1);
if (axid->bufnum1 > 0) {
regptr = &axid->region[0];
@@ -973,6 +1063,11 @@
op_mode = vfe2x_ctrl->start_cmd.mode_of_operation;
return rc;
}
+ if (vfecmd.id == VFE_CMD_RECONFIG_VFE) {
+ CDBG("VFE is RECONFIGURED\n");
+ vfe2x_ctrl->reconfig_vfe = 1;
+ return 0;
+ }
if (vfecmd.length > 256 - 4) {
cmd_data_alloc =
cmd_data = kmalloc(vfecmd.length + 4, GFP_ATOMIC);
@@ -1002,13 +1097,12 @@
if (queue == QDSP_CMDQUEUE) {
switch (vfecmd.id) {
case VFE_CMD_RESET:
- msm_adsp_enable(qcam_mod);
- msm_adsp_enable(vfe_mod);
msm_camio_vfe_blk_reset();
vfestopped = 0;
break;
case VFE_CMD_START:
case VFE_CMD_CAPTURE:
+ case VFE_CMD_CAPTURE_RAW:
spin_lock_irqsave(&vfe2x_ctrl->table_lock,
flags);
if (!list_empty(&vfe2x_ctrl->table_q)) {
@@ -1041,9 +1135,63 @@
} /* QDSP_CMDQUEUE */
}
break;
- case CMD_AXI_CFG_PREVIEW: {
- CDBG("CMD_AXI_CFG_PREVIEW\n");
+ case CMD_AXI_CFG_SEC: {
+ CDBG("CMD_AXI_CFG_SEC\n");
raw_mode = 0;
+ vfe2x_ctrl->output_mode = OUTPUT_SEC;
+ axio = kmalloc(sizeof(struct axiout), GFP_ATOMIC);
+ if (!axio) {
+ pr_err("NULL axio\n");
+ rc = -ENOMEM;
+ goto config_failure;
+ }
+
+ if (copy_from_user((char *)axio + 4,
+ (void __user *)(vfecmd.value),
+ sizeof(struct axiout))) {
+ CDBG("copy_from_user failed\n");
+ rc = -EFAULT;
+ goto config_done;
+ }
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_CAPTURE,
+ VFE_MSG_OUTPUT_SECONDARY);
+ else
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_PREVIEW,
+ VFE_MSG_OUTPUT_SECONDARY);
+ if (rc < 0) {
+ pr_err("%s error configuring pingpong buffers"
+ " for preview", __func__);
+ rc = -EINVAL;
+ goto config_done;
+ }
+
+ if (!(op_mode & SNAPSHOT_MASK_MODE))
+ free_buf = vfe2x_check_free_buffer(
+ VFE_MSG_OUTPUT_IRQ,
+ VFE_MSG_OUTPUT_SECONDARY);
+ header = cmds_map[vfecmd.id].vfe_id;
+ queue = cmds_map[vfecmd.id].queue;
+ if (header == -1 && queue == -1) {
+ rc = -EFAULT;
+ goto config_done;
+ }
+ *(uint32_t *)axio = header;
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ vfe_7x_config_axi(OUTPUT_SEC,
+ &vfe2x_ctrl->thumb, axio);
+ else
+ vfe_7x_config_axi(OUTPUT_SEC,
+ &vfe2x_ctrl->video, axio);
+ cmd_data = axio;
+ }
+ break;
+ case CMD_AXI_CFG_PRIM: {
+ CDBG("CMD_AXI_CFG_PRIM : %d\n", op_mode);
+ raw_mode = 0;
+ vfe2x_ctrl->output_mode = OUTPUT_PRIM;
axio = kmalloc(sizeof(struct axiout), GFP_ATOMIC);
if (!axio) {
pr_err("NULL axio\n");
@@ -1058,18 +1206,40 @@
rc = -EFAULT;
goto config_done;
}
- rc = vfe2x_configure_pingpong_buffers(VFE_MSG_V2X_PREVIEW,
- VFE_MSG_OUTPUT_P);
- if (rc < 0) {
- pr_err("%s error configuring pingpong buffers"
- " for preview", __func__);
- rc = -EINVAL;
- goto config_done;
- }
-
- free_buf = vfe2x_check_free_buffer(
+ if (!vfe2x_ctrl->reconfig_vfe) {
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_CAPTURE,
+ VFE_MSG_OUTPUT_PRIMARY);
+ else
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_PREVIEW,
+ VFE_MSG_OUTPUT_PRIMARY);
+ if (rc < 0) {
+ pr_err("%s error configuring pingpong buffers"
+ " for preview", __func__);
+ rc = -EINVAL;
+ goto config_done;
+ }
+ if (!(op_mode & SNAPSHOT_MASK_MODE))
+ free_buf = vfe2x_check_free_buffer(
VFE_MSG_OUTPUT_IRQ,
- VFE_MSG_OUTPUT_P);
+ VFE_MSG_OUTPUT_PRIMARY);
+ } else {
+ vfe2x_ctrl->prev.ping.ch_paddr[0] =
+ vfe2x_ctrl->free_buf.buf[0].ch_paddr[0];
+ vfe2x_ctrl->prev.ping.ch_paddr[1] =
+ vfe2x_ctrl->free_buf.buf[0].ch_paddr[1];
+ vfe2x_ctrl->prev.pong.ch_paddr[0] =
+ vfe2x_ctrl->free_buf.buf[1].ch_paddr[0];
+ vfe2x_ctrl->prev.pong.ch_paddr[1] =
+ vfe2x_ctrl->free_buf.buf[1].ch_paddr[1];
+ vfe2x_ctrl->prev.free_buf.ch_paddr[0] =
+ vfe2x_ctrl->free_buf.buf[2].ch_paddr[0];
+ vfe2x_ctrl->prev.free_buf.ch_paddr[1] =
+ vfe2x_ctrl->free_buf.buf[2].ch_paddr[1];
+ vfe2x_ctrl->reconfig_vfe = 0;
+ }
header = cmds_map[vfecmd.id].vfe_id;
queue = cmds_map[vfecmd.id].queue;
if (header == -1 && queue == -1) {
@@ -1077,12 +1247,93 @@
goto config_done;
}
*(uint32_t *)axio = header;
- vfe_7x_config_axi(OUTPUT_2, &vfe2x_ctrl->prev, axio);
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ vfe_7x_config_axi(OUTPUT_PRIM, &vfe2x_ctrl->snap, axio);
+ else
+ vfe_7x_config_axi(OUTPUT_PRIM, &vfe2x_ctrl->prev, axio);
+ cmd_data = axio;
+ }
+ break;
+ case CMD_AXI_CFG_SEC|CMD_AXI_CFG_PRIM: {
+ CDBG("CMD_AXI_CFG_SEC|PRIM\n");
+ raw_mode = 0;
+ vfe2x_ctrl->output_mode = OUTPUT_SEC|OUTPUT_PRIM;
+ axio = kmalloc(sizeof(struct axiout), GFP_ATOMIC);
+ if (!axio) {
+ pr_err("NULL axio\n");
+ rc = -ENOMEM;
+ goto config_failure;
+ }
+
+ if (copy_from_user((char *)axio + 4,
+ (void __user *)(vfecmd.value),
+ sizeof(struct axiout))) {
+ pr_err("copy_from_user failed\n");
+ rc = -EFAULT;
+ goto config_done;
+ }
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_CAPTURE,
+ VFE_MSG_OUTPUT_SECONDARY);
+ else
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_PREVIEW,
+ VFE_MSG_OUTPUT_SECONDARY);
+ if (rc < 0) {
+ pr_err("%s error configuring pingpong buffers"
+ " for preview", __func__);
+ rc = -EINVAL;
+ goto config_done;
+ }
+
+ if (!(op_mode & SNAPSHOT_MASK_MODE))
+ free_buf = vfe2x_check_free_buffer(
+ VFE_MSG_OUTPUT_IRQ,
+ VFE_MSG_OUTPUT_SECONDARY);
+ header = cmds_map[vfecmd.id].vfe_id;
+ queue = cmds_map[vfecmd.id].queue;
+ if (header == -1 && queue == -1) {
+ rc = -EFAULT;
+ goto config_done;
+ }
+ *(uint32_t *)axio = header;
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ vfe_7x_config_axi(OUTPUT_SEC, &vfe2x_ctrl->thumb, axio);
+ else
+ vfe_7x_config_axi(OUTPUT_SEC, &vfe2x_ctrl->prev, axio);
+
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_CAPTURE,
+ VFE_MSG_OUTPUT_PRIMARY);
+ else
+ rc = vfe2x_configure_pingpong_buffers(
+ VFE_MSG_V2X_PREVIEW,
+ VFE_MSG_OUTPUT_PRIMARY);
+ if (rc < 0) {
+ pr_err("%s error configuring pingpong buffers"
+ " for preview", __func__);
+ rc = -EINVAL;
+ goto config_done;
+ }
+
+ if (!(op_mode & SNAPSHOT_MASK_MODE))
+ free_buf = vfe2x_check_free_buffer(
+ VFE_MSG_OUTPUT_IRQ,
+ VFE_MSG_OUTPUT_PRIMARY);
+ if (op_mode & SNAPSHOT_MASK_MODE)
+ vfe_7x_config_axi(OUTPUT_PRIM,
+ &vfe2x_ctrl->snap, axio);
+ else
+ vfe_7x_config_axi(OUTPUT_PRIM,
+ &vfe2x_ctrl->prev, axio);
cmd_data = axio;
}
break;
case CMD_RAW_PICT_AXI_CFG: {
CDBG("CMD_RAW_PICT_AXI_CFG:%d\n", op_mode);
+ vfe2x_ctrl->output_mode = OUTPUT_PRIM;
raw_mode = 1;
axio = kmalloc(sizeof(struct axiout), GFP_ATOMIC);
if (!axio) {
@@ -1099,7 +1350,7 @@
header = cmds_map[vfecmd.id].vfe_id;
queue = cmds_map[vfecmd.id].queue;
rc = vfe2x_configure_pingpong_buffers(VFE_MSG_V2X_CAPTURE,
- VFE_MSG_OUTPUT_S);
+ VFE_MSG_OUTPUT_PRIMARY);
if (rc < 0) {
pr_err("%s error configuring pingpong buffers"
" for preview", __func__);
@@ -1111,50 +1362,7 @@
goto config_done;
}
*(uint32_t *)axio = header;
- vfe_7x_config_axi(OUTPUT_1_AND_2, &vfe2x_ctrl->snap, axio);
- cmd_data = axio;
- }
- break;
- case CMD_AXI_CFG_SNAP: {
- raw_mode = 0;
- CDBG("CMD_AXI_CFG_SNAP :%d\n", op_mode);
- axio = kmalloc(sizeof(struct axiout), GFP_ATOMIC);
- if (!axio) {
- rc = -ENOMEM;
- goto config_failure;
- }
-
- if (copy_from_user((char *)axio + 4,
- (void __user *)(vfecmd.value),
- sizeof(struct axiout))) {
- rc = -EFAULT;
- goto config_done;
- }
- header = cmds_map[vfecmd.id].vfe_id;
- queue = cmds_map[vfecmd.id].queue;
- rc = vfe2x_configure_pingpong_buffers(VFE_MSG_V2X_CAPTURE,
- VFE_MSG_OUTPUT_S);
- if (rc < 0) {
- pr_err("%s error configuring pingpong buffers"
- " for preview", __func__);
- rc = -EINVAL;
- goto config_done;
- }
- if (header == -1 && queue == -1) {
- rc = -EFAULT;
- goto config_done;
- }
- *(uint32_t *)axio = header;
- vfe_7x_config_axi(OUTPUT_1_AND_2, &vfe2x_ctrl->snap, axio);
- rc = vfe2x_configure_pingpong_buffers(VFE_MSG_V2X_CAPTURE,
- VFE_MSG_OUTPUT_T);
- if (rc < 0) {
- pr_err("%s error configuring pingpong buffers"
- " for preview", __func__);
- rc = -EINVAL;
- goto config_done;
- }
- vfe_7x_config_axi(OUTPUT_1, &vfe2x_ctrl->thumb, axio);
+ vfe_7x_config_axi(OUTPUT_PRIM, &vfe2x_ctrl->snap, axio);
cmd_data = axio;
}
break;
@@ -1169,6 +1377,7 @@
CDBG("send adsp command = %d\n", *(uint32_t *)cmd_data);
if (queue == QDSP_TABLEQUEUE &&
vfe2x_ctrl->tableack_pending) {
+ CDBG("store table cmd\n");
table_pending = kzalloc(sizeof(struct table_cmd), GFP_ATOMIC);
if (!table_pending) {
rc = -ENOMEM;
@@ -1188,12 +1397,14 @@
spin_unlock_irqrestore(&vfe2x_ctrl->table_lock, flags);
} else {
if (queue == QDSP_TABLEQUEUE) {
+ CDBG("sending table cmd\n");
spin_lock_irqsave(&vfe2x_ctrl->table_lock, flags);
rc = msm_adsp_write(vfe_mod, queue,
cmd_data, vfecmd.length + 4);
vfe2x_ctrl->tableack_pending = 1;
spin_unlock_irqrestore(&vfe2x_ctrl->table_lock, flags);
} else {
+ CDBG("send n-table cmd\n");
if (*(uint32_t *)cmd_data == VFE_OUTPUT2_ACK) {
uint32_t *ptr = cmd_data;
CDBG("%x %x %x\n", ptr[0], ptr[1], ptr[2]);
@@ -1263,6 +1474,8 @@
rc = -EBUSY;
goto get_vfe_fail;
}
+ msm_adsp_enable(qcam_mod);
+ msm_adsp_enable(vfe_mod);
return 0;
get_vfe_fail:
@@ -1287,6 +1500,7 @@
void msm_vfe_subdev_release(struct platform_device *pdev)
{
+ CDBG("msm_cam_clk_enable: disable vfe_clk\n");
msm_cam_clk_enable(&vfe2x_ctrl->pdev->dev, vfe2x_clk_info,
vfe2x_ctrl->vfe_clk, ARRAY_SIZE(vfe2x_clk_info), 0);
vfe_syncdata = NULL;
diff --git a/drivers/media/video/msm/msm_vfe7x27a_v4l2.h b/drivers/media/video/msm/msm_vfe7x27a_v4l2.h
index 0f7fb60..33d6c17 100644
--- a/drivers/media/video/msm/msm_vfe7x27a_v4l2.h
+++ b/drivers/media/video/msm/msm_vfe7x27a_v4l2.h
@@ -51,6 +51,10 @@
struct msm_free_buf free_buf;
} __packed;
+struct prev_free_buf_info {
+ struct msm_free_buf buf[3];
+};
+
struct vfe_cmd_start {
uint32_t input_source:1;
uint32_t mode_of_operation:1;
@@ -75,10 +79,13 @@
} __packed;
struct vfe2x_ctrl_type {
+ uint16_t output_mode;
struct buf_info prev;
+ struct buf_info video;
struct buf_info snap;
struct buf_info raw;
struct buf_info thumb;
+ struct prev_free_buf_info free_buf;
spinlock_t table_lock;
struct list_head table_q;
@@ -97,6 +104,7 @@
struct platform_device *pdev;
struct clk *vfe_clk[3];
spinlock_t sd_notify_lock;
+ uint32_t reconfig_vfe;
} __packed;
struct vfe_frame_extra {
@@ -379,6 +387,21 @@
int state;
int timeout;
};
+struct vfe_error_msg {
+ unsigned int camif_error:1;
+ unsigned int output1ybusoverflow:1;
+ unsigned int output1cbcrbusoverflow:1;
+ unsigned int output2ybusoverflow:1;
+ unsigned int output2cbcrbusoverflow:1;
+ unsigned int autofocusstatbusoverflow:1;
+ unsigned int wb_expstatbusoverflow:1;
+ unsigned int axierror:1;
+ unsigned int /* reserved */ : 24;
+ unsigned int camif_staus:1;
+ unsigned int pixel_count:14;
+ unsigned int line_count:14;
+ unsigned int /*reserved */ : 3;
+} __packed;
static struct msm_free_buf *vfe2x_check_free_buffer(int id, int path);
diff --git a/drivers/media/video/msm/sensors/mt9e013_v4l2.c b/drivers/media/video/msm/sensors/mt9e013_v4l2.c
index 924cbc9..a6bc653 100644
--- a/drivers/media/video/msm/sensors/mt9e013_v4l2.c
+++ b/drivers/media/video/msm/sensors/mt9e013_v4l2.c
@@ -28,12 +28,6 @@
};
static struct msm_camera_i2c_reg_conf mt9e013_prev_settings[] = {
- {0x0300, 0x0004},/*VT_PIX_CLK_DIV*/
- {0x0302, 0x0001},/*VT_SYS_CLK_DIV*/
- {0x0304, 0x0002},/*PRE_PLL_CLK_DIV*/
- {0x0306, 0x003A},/*PLL_MULTIPLIER*/
- {0x0308, 0x000A},/*OP_PIX_CLK_DIV*/
- {0x030A, 0x0001},/*OP_SYS_CLK_DIV*/
/*Output Size (1632x1224)*/
{0x0344, 0x0008},/*X_ADDR_START*/
{0x0348, 0x0CC9},/*X_ADDR_END*/
@@ -56,12 +50,6 @@
};
static struct msm_camera_i2c_reg_conf mt9e013_snap_settings[] = {
- {0x0300, 0x0004},/*VT_PIX_CLK_DIV*/
- {0x0302, 0x0001},/*VT_SYS_CLK_DIV*/
- {0x0304, 0x0002},/*PRE_PLL_CLK_DIV*/
- {0x0306, 0x003A},/*PLL_MULTIPLIER*/
- {0x0308, 0x000A},/*OP_PIX_CLK_DIV*/
- {0x030A, 0x0001},/*OP_SYS_CLK_DIV*/
/*Output Size (3264x2448)*/
{0x0344, 0x0000},/*X_ADDR_START */
{0x0348, 0x0CCF},/*X_ADDR_END*/
@@ -172,14 +160,14 @@
{0x31B8, 0x0E3F},/*MIPI_TIMING_2*/
/*set data to RAW10 format*/
{0x0112, 0x0A0A},/*CCP_DATA_FORMAT*/
- {0x30F0, 0x8000},/*VCM CONTROL*/
+ {0x30F0, 0x800D},/*VCM CONTROL*/
{0x3044, 0x0590},
{0x306E, 0xFC80},
{0x30B2, 0xC000},
{0x30D6, 0x0800},
{0x316C, 0xB42F},
- {0x316E, 0x869C},
+ {0x316E, 0x869A},
{0x3170, 0x210E},
{0x317A, 0x010E},
{0x31E0, 0x1FB9},
@@ -188,17 +176,19 @@
{0x37C2, 0x0000},
{0x37C4, 0x0000},
{0x37C6, 0x0000},
+ {0x3E00, 0x0011},
{0x3E02, 0x8801},
- {0x3E04, 0x2301},
+ {0x3E04, 0x2801},
{0x3E06, 0x8449},
{0x3E08, 0x6841},
{0x3E0A, 0x400C},
{0x3E0C, 0x1001},
- {0x3E0E, 0x2103},
+ {0x3E0E, 0x2603},
{0x3E10, 0x4B41},
- {0x3E12, 0x4B26},
+ {0x3E12, 0x4B24},
+ {0x3E14, 0xA3CF},
{0x3E16, 0x8802},
- {0x3E18, 0x84FF},
+ {0x3E18, 0x8401},
{0x3E1A, 0x8601},
{0x3E1C, 0x8401},
{0x3E1E, 0x840A},
@@ -207,41 +197,56 @@
{0x3E24, 0x00FF},
{0x3E26, 0x0088},
{0x3E28, 0x2E8A},
+ {0x3E30, 0x0000},
{0x3E32, 0x8801},
- {0x3E34, 0x4024},
+ {0x3E34, 0x4029},
+ {0x3E36, 0x00FF},
{0x3E38, 0x8469},
- {0x3E3C, 0x2301},
- {0x3E3E, 0x3E25},
+ {0x3E3A, 0x00FF},
+ {0x3E3C, 0x2801},
+ {0x3E3E, 0x3E2A},
{0x3E40, 0x1C01},
- {0x3E42, 0x8486},
+ {0x3E42, 0xFF84},
{0x3E44, 0x8401},
- {0x3E46, 0x00FF},
+ {0x3E46, 0x0C01},
{0x3E48, 0x8401},
- {0x3E4A, 0x8601},
+ {0x3E4A, 0x00FF},
{0x3E4C, 0x8402},
- {0x3E4E, 0x00FF},
- {0x3E50, 0x6623},
+ {0x3E4E, 0x8984},
+ {0x3E50, 0x6628},
{0x3E52, 0x8340},
{0x3E54, 0x00FF},
{0x3E56, 0x4A42},
- {0x3E58, 0x2203},
- {0x3E5A, 0x674D},
- {0x3E5C, 0x3F25},
+ {0x3E58, 0x2703},
+ {0x3E5A, 0x6752},
+ {0x3E5C, 0x3F2A},
{0x3E5E, 0x846A},
{0x3E60, 0x4C01},
{0x3E62, 0x8401},
{0x3E66, 0x3901},
+ {0x3E90, 0x2C01},
+ {0x3E98, 0x2B02},
+ {0x3E92, 0x2A04},
+ {0x3E94, 0x2509},
+ {0x3E96, 0x0000},
+ {0x3E9A, 0x2905},
+ {0x3E9C, 0x00FF},
{0x3ECC, 0x00EB},
{0x3ED0, 0x1E24},
{0x3ED4, 0xAFC4},
{0x3ED6, 0x909B},
- {0x3ED8, 0x0006},
- {0x3EDA, 0xCFC6},
- {0x3EDC, 0x4FE4},
{0x3EE0, 0x2424},
{0x3EE2, 0x9797},
{0x3EE4, 0xC100},
- {0x3EE6, 0x0540}
+ {0x3EE6, 0x0540},
+ {0x3174, 0x8000},
+ /* PLL settings */
+ {0x0300, 0x0004},/*VT_PIX_CLK_DIV*/
+ {0x0302, 0x0001},/*VT_SYS_CLK_DIV*/
+ {0x0304, 0x0002},/*PRE_PLL_CLK_DIV*/
+ {0x0306, 0x003A},/*PLL_MULTIPLIER*/
+ {0x0308, 0x000A},/*OP_PIX_CLK_DIV*/
+ {0x030A, 0x0001},/*OP_SYS_CLK_DIV*/
};
static struct v4l2_subdev_info mt9e013_subdev_info[] = {
@@ -498,6 +503,7 @@
.sensor_v4l2_subdev_info_size = ARRAY_SIZE(mt9e013_subdev_info),
.sensor_v4l2_subdev_ops = &mt9e013_subdev_ops,
.func_tbl = &mt9e013_func_tbl,
+ .clk_rate = MSM_SENSOR_MCLK_24HZ,
};
module_init(msm_sensor_init_module);
diff --git a/drivers/media/video/msm/sensors/ov9726_v4l2.c b/drivers/media/video/msm/sensors/ov9726_v4l2.c
index e345717..17291ff 100644
--- a/drivers/media/video/msm/sensors/ov9726_v4l2.c
+++ b/drivers/media/video/msm/sensors/ov9726_v4l2.c
@@ -271,6 +271,7 @@
.sensor_v4l2_subdev_info_size = ARRAY_SIZE(ov9726_subdev_info),
.sensor_v4l2_subdev_ops = &ov9726_subdev_ops,
.func_tbl = &ov9726_func_tbl,
+ .clk_rate = MSM_SENSOR_MCLK_24HZ,
};
module_init(msm_sensor_init_module);
diff --git a/drivers/media/video/msm/sensors/s5k4e1_v4l2.c b/drivers/media/video/msm/sensors/s5k4e1_v4l2.c
index 1f99119..699f0dd 100644
--- a/drivers/media/video/msm/sensors/s5k4e1_v4l2.c
+++ b/drivers/media/video/msm/sensors/s5k4e1_v4l2.c
@@ -196,8 +196,8 @@
.y_output = 0x7A8,
.line_length_pclk = 0xAB2,
.frame_length_lines = 0x7B4,
- .vt_pixel_clk = 816000000,
- .op_pixel_clk = 816000000,
+ .vt_pixel_clk = 81600000,
+ .op_pixel_clk = 81600000,
.binning_factor = 0,
},
{
@@ -205,8 +205,8 @@
.y_output = 0x3D4,
.line_length_pclk = 0xAB2,
.frame_length_lines = 0x3E0,
- .vt_pixel_clk = 816000000,
- .op_pixel_clk = 816000000,
+ .vt_pixel_clk = 81600000,
+ .op_pixel_clk = 81600000,
.binning_factor = 1,
},
};
@@ -349,8 +349,6 @@
gain = max_legal_gain;
}
- gain = 32;
- line = 1465;
pr_info("s5k4e1_write_exp_gain : gain = %d line = %d\n", gain, line);
line = (uint32_t) (line * s_ctrl->fps_divider);
fl_lines = s_ctrl->curr_frame_length_lines * s_ctrl->fps_divider / Q10;
@@ -494,6 +492,7 @@
.sensor_v4l2_subdev_info_size = ARRAY_SIZE(s5k4e1_subdev_info),
.sensor_v4l2_subdev_ops = &s5k4e1_subdev_ops,
.func_tbl = &s5k4e1_func_tbl,
+ .clk_rate = MSM_SENSOR_MCLK_24HZ,
};
module_init(msm_sensor_init_module);
diff --git a/include/media/msm_isp.h b/include/media/msm_isp.h
index e02597a..cb728a0 100644
--- a/include/media/msm_isp.h
+++ b/include/media/msm_isp.h
@@ -199,6 +199,7 @@
#define VFE_CMD_SCALE_OUTPUT2_CONFIG 135
#define VFE_CMD_CAPTURE_RAW 136
#define VFE_CMD_STOP_LIVESHOT 137
+#define VFE_CMD_RECONFIG_VFE 138
struct msm_isp_cmd {
int32_t id;