Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 59503737 authored by Jeyaprakash Soundrapandian's avatar Jeyaprakash Soundrapandian Committed by Gerrit - the friendly Code Review server
Browse files

Merge "msm: camera: csid: Halt the device in case of input errors" into dev/msm-4.9-camx

parents 114a1f76 71e72494
Loading
Loading
Loading
Loading
+71 −11
Original line number Diff line number Diff line
@@ -1884,21 +1884,23 @@ static int cam_ife_csid_disable_rdi_path(

	if (res->res_id >= CAM_IFE_PIX_PATH_RES_MAX ||
		!csid_reg->rdi_reg[res->res_id]) {
		CAM_DBG(CAM_ISP, "CSID:%d Invalid res id%d",
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d Invalid res id%d",
			csid_hw->hw_intf->hw_idx, res->res_id);
		return -EINVAL;
	}

	if (res->res_state == CAM_ISP_RESOURCE_STATE_INIT_HW ||
		res->res_state == CAM_ISP_RESOURCE_STATE_RESERVED) {
		CAM_DBG(CAM_ISP, "CSID:%d Res:%d already in stopped state:%d",
		CAM_ERR_RATE_LIMIT(CAM_ISP,
			"CSID:%d Res:%d already in stopped state:%d",
			csid_hw->hw_intf->hw_idx,
			res->res_id, res->res_state);
		return rc;
	}

	if (res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING) {
		CAM_DBG(CAM_ISP, "CSID:%d Res:%d Invalid res_state%d",
		CAM_ERR_RATE_LIMIT(CAM_ISP,
			"CSID:%d Res:%d Invalid res_state%d",
			csid_hw->hw_intf->hw_idx, res->res_id,
			res->res_state);
		return -EINVAL;
@@ -2006,21 +2008,23 @@ static int cam_ife_csid_res_wait_for_halt(
	soc_info = &csid_hw->hw_info->soc_info;

	if (res->res_id >= CAM_IFE_PIX_PATH_RES_MAX) {
		CAM_DBG(CAM_ISP, "CSID:%d Invalid res id%d",
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d Invalid res id%d",
			csid_hw->hw_intf->hw_idx, res->res_id);
		return -EINVAL;
	}

	if (res->res_state == CAM_ISP_RESOURCE_STATE_INIT_HW ||
		res->res_state == CAM_ISP_RESOURCE_STATE_RESERVED) {
		CAM_DBG(CAM_ISP, "CSID:%d Res:%d already in stopped state:%d",
		CAM_ERR_RATE_LIMIT(CAM_ISP,
			"CSID:%d Res:%d already in stopped state:%d",
			csid_hw->hw_intf->hw_idx,
			res->res_id, res->res_state);
		return rc;
	}

	if (res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING) {
		CAM_DBG(CAM_ISP, "CSID:%d Res:%d Invalid state%d",
		CAM_ERR_RATE_LIMIT(CAM_ISP,
			"CSID:%d Res:%d Invalid state%d",
			csid_hw->hw_intf->hw_idx, res->res_id,
			res->res_state);
		return -EINVAL;
@@ -2489,8 +2493,7 @@ static int cam_ife_csid_stop(void *hw_priv,
	/*wait for the path to halt */
	for (i = 0; i < csid_stop->num_res; i++) {
		res = csid_stop->node_res[i];
		if (res->res_type == CAM_ISP_RESOURCE_PIX_PATH &&
			csid_stop->stop_cmd == CAM_CSID_HALT_AT_FRAME_BOUNDARY)
		if (csid_stop->stop_cmd == CAM_CSID_HALT_AT_FRAME_BOUNDARY)
			rc = cam_ife_csid_res_wait_for_halt(csid_hw, res);
		else
			res->res_state = CAM_ISP_RESOURCE_STATE_INIT_HW;
@@ -2548,8 +2551,35 @@ static int cam_ife_csid_process_cmd(void *hw_priv,

}

static int cam_ife_csid_halt_device(
	struct cam_ife_csid_hw *csid_hw)
{
	uint32_t  i;
	int rc = 0;
	struct cam_isp_resource_node *res_node;

	res_node = &csid_hw->ipp_res;
	if (res_node->res_state == CAM_ISP_RESOURCE_STATE_STREAMING) {
		rc = cam_ife_csid_disable_ipp_path(csid_hw,
			res_node, CAM_CSID_HALT_IMMEDIATELY);
		res_node->res_state = CAM_ISP_RESOURCE_STATE_INIT_HW;
	}

	for (i = 0; i < CAM_IFE_CSID_RDI_MAX; i++) {
		res_node = &csid_hw->rdi_res[i];
		if (res_node->res_state == CAM_ISP_RESOURCE_STATE_STREAMING) {
			rc = cam_ife_csid_disable_rdi_path(csid_hw,
				res_node, CAM_CSID_HALT_IMMEDIATELY);
			res_node->res_state = CAM_ISP_RESOURCE_STATE_INIT_HW;
		}
	}
	return rc;
}


irqreturn_t cam_ife_csid_irq(int irq_num, void *data)
{
	int rc = 0;
	struct cam_ife_csid_hw          *csid_hw;
	struct cam_hw_soc_info          *soc_info;
	struct cam_ife_csid_reg_offset  *csid_reg;
@@ -2623,22 +2653,52 @@ irqreturn_t cam_ife_csid_irq(int irq_num, void *data)
	if (irq_status_rx & CSID_CSI2_RX_ERROR_LANE0_FIFO_OVERFLOW) {
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d lane 0 over flow",
			 csid_hw->hw_intf->hw_idx);
		rc = cam_ife_csid_halt_device(csid_hw);
		if (rc) {
			CAM_ERR_RATE_LIMIT(CAM_ISP,
				"CSID:%d csid halt device fail rc = %d",
				csid_hw->hw_intf->hw_idx, rc);
		}
	}
	if (irq_status_rx & CSID_CSI2_RX_ERROR_LANE1_FIFO_OVERFLOW) {
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d lane 1 over flow",
			 csid_hw->hw_intf->hw_idx);
		rc = cam_ife_csid_halt_device(csid_hw);
		if (rc) {
			CAM_ERR_RATE_LIMIT(CAM_ISP,
				"CSID:%d csid halt device fail rc = %d",
				csid_hw->hw_intf->hw_idx, rc);
		}
	}
	if (irq_status_rx & CSID_CSI2_RX_ERROR_LANE2_FIFO_OVERFLOW) {
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d lane 2 over flow",
			 csid_hw->hw_intf->hw_idx);
		rc = cam_ife_csid_halt_device(csid_hw);
		if (rc) {
			CAM_ERR_RATE_LIMIT(CAM_ISP,
				"CSID:%d csid halt device fail rc = %d",
				csid_hw->hw_intf->hw_idx, rc);
		}
	}
	if (irq_status_rx & CSID_CSI2_RX_ERROR_LANE3_FIFO_OVERFLOW) {
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d lane 3 over flow",
			 csid_hw->hw_intf->hw_idx);
		rc = cam_ife_csid_halt_device(csid_hw);
		if (rc) {
			CAM_ERR_RATE_LIMIT(CAM_ISP,
				"CSID:%d csid halt device fail rc = %d",
				csid_hw->hw_intf->hw_idx, rc);
		}
	}
	if (irq_status_rx & CSID_CSI2_RX_ERROR_TG_FIFO_OVERFLOW) {
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d TG OVER  FLOW",
			 csid_hw->hw_intf->hw_idx);
		rc = cam_ife_csid_halt_device(csid_hw);
		if (rc) {
			CAM_ERR_RATE_LIMIT(CAM_ISP,
				"CSID:%d csid halt device fail rc = %d",
				csid_hw->hw_intf->hw_idx, rc);
		}
	}
	if (irq_status_rx & CSID_CSI2_RX_ERROR_CPHY_EOT_RECEPTION) {
		CAM_ERR_RATE_LIMIT(CAM_ISP, "CSID:%d CPHY_EOT_RECEPTION",