Forráskód Böngészése

Merge changes Ifd44dc75,Ieb6f1245,I16d53737,I34c5227b,I56dc1091, ... into camera-kernel.lnx.7.0

* changes:
  msm: camera: tfe: Add out of sync error handling
  msm: camera: tfe: Add PDAF support in tfe 770 header
  msm: camera: common: update msm-mmrm dependency to camera-kernel
  msm: camera: tfe: Add TFE and TFE LITE header file for 770 HW
  msm: camera: isp: Add support for PDAF HW
  msm: camera: tfe: Remove hardcoding of shift values
  msm: camera: isp: Add support for CSID 770
  msm: camera: tfe: Add support for TFE LITE HW
  msm: camera: tfe: Add MUP support for TFE HW
Camera Software Integration 1 éve
szülő
commit
ff07076ebe
29 módosított fájl, 4039 hozzáadás és 201 törlés
  1. 1 1
      Android.mk
  2. 3 0
      drivers/cam_isp/cam_isp_context.c
  3. 1 1
      drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c
  4. 338 54
      drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c
  5. 8 0
      drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.h
  6. 7 4
      drivers/cam_isp/isp_hw_mgr/hw_utils/cam_isp_packet_parser.c
  7. 3 1
      drivers/cam_isp/isp_hw_mgr/hw_utils/include/cam_isp_packet_parser.h
  8. 15 0
      drivers/cam_isp/isp_hw_mgr/include/cam_isp_hw_mgr_intf.h
  9. 2 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_isp_hw.h
  10. 8 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_tfe_csid_hw_intf.h
  11. 4 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_tfe_hw_intf.h
  12. 11 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid.c
  13. 363 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid770.h
  14. 486 25
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_core.c
  15. 43 14
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_core.h
  16. 4 1
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_soc.c
  17. 3 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_soc.h
  18. 16 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe.c
  19. 21 2
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe530.h
  20. 21 2
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe640.h
  21. 1423 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe770.h
  22. 161 18
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_bus.c
  23. 12 1
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_bus.h
  24. 422 69
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_core.c
  25. 75 8
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_core.h
  26. 580 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_lite770.h
  27. 5 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_soc.c
  28. 2 0
      drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_soc.h
  29. 1 0
      include/uapi/camera/media/cam_tfe.h

+ 1 - 1
Android.mk

@@ -16,7 +16,7 @@ DLKM_DIR := $(TOP)/device/qcom/common/dlkm
 LOCAL_MODULE_DDK_BUILD := true
 
 # List of board platforms for which MMRM driver API should be enabled
-MMRM_BOARDS := taro parrot kalama pineapple
+MMRM_BOARDS := taro parrot kalama pineapple crow
 
 # List of board platforms for which Synx V2 vendor driver API should be enabled
 SYNX_VENDOR_BOARDS := pineapple

+ 3 - 0
drivers/cam_isp/cam_isp_context.c

@@ -1324,6 +1324,9 @@ static const char *__cam_isp_tfe_resource_handle_id_to_type(
 	case CAM_ISP_TFE_OUT_RES_DS4:                   return "TFE_DS_4";
 	case CAM_ISP_TFE_OUT_RES_DS16:                  return "TFE_DS_16";
 	case CAM_ISP_TFE_OUT_RES_AI:                    return "TFE_AI";
+	case CAM_ISP_TFE_OUT_RES_PD_LCR_STATS:          return "TFE_LCR_STATS";
+	case CAM_ISP_TFE_OUT_RES_PD_PREPROCESSED:       return "TFE_PD_PREPROCESSED";
+	case CAM_ISP_TFE_OUT_RES_PD_PARSED:             return "TFE_PD_PARSED";
 	/* Handle invalid type */
 	default:                                        return "Invalid_Resource_Type";
 	}

+ 1 - 1
drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c

@@ -12791,7 +12791,7 @@ static int cam_ife_mgr_isp_add_reg_update(struct cam_ife_hw_mgr_ctx *ctx,
 		rc = cam_isp_add_reg_update(prepare,
 			&ctx->res_list_ife_src,
 			ctx->base[i].idx, kmd_buf,
-			!ctx->flags.internal_cdm);
+			!ctx->flags.internal_cdm, NULL);
 
 		if (rc) {
 			CAM_ERR(CAM_ISP,

+ 338 - 54
drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c

@@ -32,6 +32,7 @@
 
 #define CAM_TFE_HW_CONFIG_TIMEOUT 60
 #define CAM_TFE_HW_CONFIG_WAIT_MAX_TRY  3
+#define MAX_TFE_INTERNAL_RECOVERY_ATTEMPTS    1
 
 #define TZ_SVC_SMMU_PROGRAM 0x15
 #define TZ_SAFE_SYSCALL_ID  0x3
@@ -239,6 +240,20 @@ static int cam_tfe_mgr_get_hw_caps(void *hw_mgr_priv, void *hw_caps_args)
 	return rc;
 }
 
+static inline bool cam_tfe_hw_mgr_check_path_port_compat(
+	uint32_t in_type, uint32_t out_type)
+{
+	int i;
+	const struct cam_isp_hw_path_port_map *map = &g_tfe_hw_mgr.path_port_map;
+
+	for (i = 0; i < map->num_entries; i++) {
+		if (map->entry[i][1] == out_type)
+			return (map->entry[i][0] == in_type);
+	}
+
+	return (in_type == CAM_ISP_HW_TFE_IN_CAMIF);
+}
+
 static int cam_tfe_hw_mgr_is_rdi_res(uint32_t res_id)
 {
 	int rc = 0;
@@ -1019,6 +1034,7 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_out(
 
 		switch (tfe_in_res->res_id) {
 		case CAM_ISP_HW_TFE_IN_CAMIF:
+		case CAM_ISP_HW_TFE_IN_PDLIB:
 			rc = cam_tfe_hw_mgr_acquire_res_tfe_out_pixel(tfe_ctx,
 				tfe_in_res, in_port);
 			break;
@@ -1046,7 +1062,8 @@ err:
 static int cam_tfe_hw_mgr_acquire_res_tfe_in(
 	struct cam_tfe_hw_mgr_ctx               *tfe_ctx,
 	struct cam_isp_tfe_in_port_generic_info *in_port,
-	uint32_t                          *pdaf_enable)
+	uint32_t                          *pdaf_enable,
+	bool                              lcr_enable)
 {
 	int rc                = -EINVAL;
 	int i;
@@ -1080,6 +1097,7 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_in(
 		tfe_acquire.tfe_in.camif_pd_enable = *pdaf_enable;
 		tfe_acquire.priv = tfe_ctx;
 		tfe_acquire.event_cb = cam_tfe_hw_mgr_event_handler;
+		tfe_acquire.tfe_in.lcr_enable = lcr_enable;
 
 		switch (csid_res->res_id) {
 		case CAM_TFE_CSID_PATH_RES_IPP:
@@ -1094,6 +1112,17 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_in(
 				CAM_ISP_HW_SYNC_NONE;
 
 			break;
+		case CAM_TFE_CSID_PATH_RES_PPP:
+			tfe_acquire.tfe_in.res_id =
+				CAM_ISP_HW_TFE_IN_PDLIB;
+
+			if (csid_res->is_dual_isp)
+				tfe_acquire.tfe_in.sync_mode =
+					CAM_ISP_HW_SYNC_MASTER;
+			else
+				tfe_acquire.tfe_in.sync_mode =
+					CAM_ISP_HW_SYNC_NONE;
+			break;
 		case CAM_TFE_CSID_PATH_RES_RDI_0:
 			tfe_acquire.tfe_in.res_id = CAM_ISP_HW_TFE_IN_RDI0;
 			tfe_acquire.tfe_in.sync_mode = CAM_ISP_HW_SYNC_NONE;
@@ -1162,7 +1191,9 @@ err:
 
 static int cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(
 	struct cam_tfe_hw_mgr_ctx               *tfe_ctx,
-	struct cam_isp_tfe_in_port_generic_info *in_port)
+	struct cam_isp_tfe_in_port_generic_info *in_port,
+	bool                                is_ipp,
+	bool                                crop_enable)
 {
 	int rc = -EINVAL;
 	int i, j;
@@ -1170,14 +1201,17 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(
 	struct cam_tfe_hw_mgr                        *tfe_hw_mgr;
 	struct cam_isp_hw_mgr_res                    *csid_res;
 	struct cam_hw_intf                           *hw_intf;
-	struct cam_tfe_csid_hw_reserve_resource_args  csid_acquire;
+	struct cam_tfe_csid_hw_reserve_resource_args  csid_acquire = {0};
 	enum cam_tfe_csid_path_res_id                 path_res_id;
 	struct cam_isp_hw_mgr_res        *csid_res_temp, *csid_res_iterator;
 	struct cam_isp_tfe_out_port_generic_info     *out_port = NULL;
 
 	tfe_hw_mgr = tfe_ctx->hw_mgr;
 	/* get csid resource */
-	path_res_id = CAM_TFE_CSID_PATH_RES_IPP;
+	if (is_ipp)
+		path_res_id = CAM_TFE_CSID_PATH_RES_IPP;
+	else
+		path_res_id = CAM_TFE_CSID_PATH_RES_PPP;
 
 	rc = cam_tfe_hw_mgr_get_res(&tfe_ctx->free_res_list, &csid_res);
 	if (rc) {
@@ -1194,6 +1228,7 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(
 	csid_acquire.node_res = NULL;
 	csid_acquire.event_cb_prv = tfe_ctx;
 	csid_acquire.event_cb = cam_tfe_hw_mgr_event_handler;
+	csid_acquire.crop_enable = crop_enable;
 	if (in_port->num_out_res)
 		out_port = &(in_port->data[0]);
 
@@ -1232,12 +1267,14 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(
 				csid_acquire.node_res;
 
 			CAM_DBG(CAM_ISP,
-				"acquired from old csid(%s)=%d CSID rsrc successfully",
+				"acquired from old csid(%s)=%d CSID rsrc %s successfully",
 				(i == 0) ? "left" : "right",
-				hw_intf->hw_idx);
+				hw_intf->hw_idx,
+				(is_ipp) ? "IPP" : "PPP");
 
 			if (in_port->usage_type && acquired_cnt == 1 &&
-				path_res_id == CAM_TFE_CSID_PATH_RES_IPP)
+				((path_res_id == CAM_TFE_CSID_PATH_RES_IPP) ||
+				(path_res_id == CAM_TFE_CSID_PATH_RES_PPP)))
 				/*
 				 * Continue to acquire Right for IPP.
 				 * Dual TFE for RDI is not currently
@@ -1284,8 +1321,9 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(
 
 		if (i == CAM_TFE_CSID_HW_NUM_MAX || !csid_acquire.node_res) {
 			CAM_ERR(CAM_ISP,
-				"Can not acquire left tfe csid path resource %d",
-				path_res_id);
+				"Can not acquire left tfe csid path resource %d (%s)",
+				path_res_id,
+				(is_ipp) ? "IPP" : "PPP");
 			goto put_res;
 		}
 	} else {
@@ -1308,14 +1346,16 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(
 
 		if (i == -1 || !csid_acquire.node_res) {
 			CAM_ERR(CAM_ISP,
-				"Can not acquire tfe csid path resource %d",
-				path_res_id);
+				"Can not acquire tfe csid path resource %d(%s)",
+				path_res_id,
+				(is_ipp) ? "IPP" : "PPP");
 			goto put_res;
 		}
 	}
 acquire_successful:
-	CAM_DBG(CAM_ISP, "CSID path left acquired success. is_dual %d",
-		in_port->usage_type);
+	CAM_DBG(CAM_ISP, "CSID path left acquired success. is_dual %d res %s",
+		in_port->usage_type,
+		(is_ipp) ? "IPP" : "PPP");
 
 	csid_res_temp->res_type = CAM_ISP_RESOURCE_PIX_PATH;
 	csid_res_temp->res_id = path_res_id;
@@ -1337,7 +1377,8 @@ acquire_successful:
 	 * Acquire Right if not already acquired.
 	 * Dual TFE for RDI is not currently supported.
 	 */
-	if (in_port->usage_type && (path_res_id == CAM_TFE_CSID_PATH_RES_IPP)
+	if (in_port->usage_type && ((path_res_id == CAM_TFE_CSID_PATH_RES_IPP)
+		|| (path_res_id == CAM_TFE_CSID_PATH_RES_PPP))
 		&& (acquired_cnt == 1)) {
 		memset(&csid_acquire, 0, sizeof(csid_acquire));
 		csid_acquire.node_res = NULL;
@@ -1349,6 +1390,7 @@ acquire_successful:
 		csid_acquire.sync_mode = CAM_ISP_HW_SYNC_SLAVE;
 		csid_acquire.node_res = NULL;
 		csid_acquire.out_port = in_port->data;
+		csid_acquire.crop_enable = crop_enable;
 		csid_acquire.event_cb_prv = tfe_ctx;
 		csid_acquire.event_cb = cam_tfe_hw_mgr_event_handler;
 
@@ -1370,14 +1412,16 @@ acquire_successful:
 
 		if (j == CAM_TFE_CSID_HW_NUM_MAX) {
 			CAM_ERR(CAM_ISP,
-				"Can not acquire tfe csid pixel resource");
+				"Can not acquire tfe csid pixel resource %s",
+				(is_ipp) ? "IPP" : "PPP");
 			goto end;
 		}
 		csid_res_temp->hw_res[1] = csid_acquire.node_res;
 		tfe_ctx->slave_hw_idx =
 			csid_res_temp->hw_res[1]->hw_intf->hw_idx;
-		CAM_DBG(CAM_ISP, "CSID right acquired success is_dual %d",
-			in_port->usage_type);
+		CAM_DBG(CAM_ISP, "CSID right acquired success is_dual %d res %s",
+			in_port->usage_type,
+			(is_ipp) ? "IPP" : "PPP");
 	}
 
 	return 0;
@@ -1427,7 +1471,7 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_rdi(
 	struct cam_isp_hw_mgr_res                   *csid_res;
 	struct cam_hw_intf                          *hw_intf;
 	struct cam_isp_tfe_out_port_generic_info    *out_port;
-	struct cam_tfe_csid_hw_reserve_resource_args csid_acquire;
+	struct cam_tfe_csid_hw_reserve_resource_args csid_acquire = {0};
 	struct cam_isp_hw_mgr_res                   *csid_res_iterator;
 	enum cam_tfe_csid_path_res_id                path_res_id;
 
@@ -1473,6 +1517,13 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_rdi(
 
 				hw_intf = csid_res_iterator->hw_res[i]->hw_intf;
 
+				if (tfe_hw_mgr->tfe_csid_dev_caps[hw_intf->hw_idx].is_lite
+					&& !tfe_ctx->is_rdi_only_context) {
+					CAM_DBG(CAM_ISP, "Ctx id %d CSID[%u] cannot use lite",
+						tfe_ctx->ctx_index, hw_intf->hw_idx);
+					continue;
+				}
+
 				rc = hw_intf->hw_ops.reserve(hw_intf->hw_priv,
 					&csid_acquire, sizeof(csid_acquire));
 				if (rc) {
@@ -1511,6 +1562,14 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_rdi(
 					continue;
 
 				hw_intf = tfe_hw_mgr->csid_devices[i];
+
+				if (tfe_hw_mgr->tfe_csid_dev_caps[hw_intf->hw_idx].is_lite &&
+					!tfe_ctx->is_rdi_only_context) {
+					CAM_DBG(CAM_ISP, "Ctx id %d CSID[%u] cannot use lite",
+						tfe_ctx->ctx_index, hw_intf->hw_idx);
+					continue;
+				}
+
 				rc = hw_intf->hw_ops.reserve(hw_intf->hw_priv,
 					&csid_acquire, sizeof(csid_acquire));
 				if (rc)
@@ -1537,6 +1596,14 @@ static int cam_tfe_hw_mgr_acquire_res_tfe_csid_rdi(
 					continue;
 
 				hw_intf = tfe_hw_mgr->csid_devices[i];
+
+				if (tfe_hw_mgr->tfe_csid_dev_caps[hw_intf->hw_idx].is_lite &&
+					!tfe_ctx->is_rdi_only_context) {
+					CAM_DBG(CAM_ISP, "Ctx id %d CSID[%u] cannot use lite",
+						tfe_ctx->ctx_index, hw_intf->hw_idx);
+					continue;
+				}
+
 				rc = hw_intf->hw_ops.reserve(hw_intf->hw_priv,
 					&csid_acquire, sizeof(csid_acquire));
 				if (rc)
@@ -1583,10 +1650,13 @@ static int cam_tfe_hw_mgr_preprocess_port(
 	struct cam_isp_tfe_in_port_generic_info *in_port,
 	int                             *ipp_count,
 	int                             *rdi_count,
-	int                             *pdaf_enable)
+	int                             *ppp_count,
+	int                             *pdaf_enable,
+	bool                            *lcr_enable)
 {
 	int ipp_num        = 0;
 	int rdi_num        = 0;
+	int pd_num         = 0;
 	bool rdi2_enable   = false;
 	uint32_t i;
 	struct cam_isp_tfe_out_port_generic_info *out_port;
@@ -1610,6 +1680,12 @@ static int cam_tfe_hw_mgr_preprocess_port(
 			rdi_num++;
 			if (out_port->res_id == CAM_ISP_TFE_OUT_RES_RDI_2)
 				rdi2_enable = true;
+		} else if (cam_tfe_hw_mgr_check_path_port_compat(CAM_ISP_HW_TFE_IN_PDLIB,
+					out_port->res_id)) {
+			pd_num++;
+
+			if (out_port->res_id == CAM_ISP_TFE_OUT_RES_PD_LCR_STATS)
+				*lcr_enable = true;
 		} else {
 			ipp_num++;
 			if (out_port->res_id == CAM_ISP_TFE_OUT_RES_PDAF)
@@ -1625,9 +1701,10 @@ static int cam_tfe_hw_mgr_preprocess_port(
 
 	*ipp_count = ipp_num;
 	*rdi_count = rdi_num;
+	*ppp_count = pd_num;
 
-	CAM_DBG(CAM_ISP, "rdi: %d ipp: %d pdaf:%d", rdi_num, ipp_num,
-		*pdaf_enable);
+	CAM_DBG(CAM_ISP, "rdi: %d ipp: %d ppp: %d pdaf:%d", rdi_num, ipp_num,
+		*ppp_count, *pdaf_enable);
 
 	return 0;
 }
@@ -1636,28 +1713,51 @@ static int cam_tfe_mgr_acquire_hw_for_ctx(
 	struct cam_tfe_hw_mgr_ctx               *tfe_ctx,
 	struct cam_isp_tfe_in_port_generic_info *in_port,
 	uint32_t *num_pix_port, uint32_t  *num_rdi_port,
-	uint32_t *pdaf_enable)
+	uint32_t  *num_pd_port, uint32_t *pdaf_enable)
 {
 	int rc                                    = -EINVAL;
 	int is_dual_isp                           = 0;
 	int ipp_count                             = 0;
 	int rdi_count                             = 0;
+	int ppp_count                             = 0;
+	bool lcr_enable                           = false;
+	bool crop_enable                          = true;
 
 	is_dual_isp = in_port->usage_type;
 
 	cam_tfe_hw_mgr_preprocess_port(tfe_ctx, in_port, &ipp_count,
-		&rdi_count, pdaf_enable);
+		&rdi_count, &ppp_count, pdaf_enable, &lcr_enable);
 
-	if (!ipp_count && !rdi_count) {
+	if (!ipp_count && !rdi_count && !ppp_count) {
 		CAM_ERR(CAM_ISP,
 			"No PIX or RDI");
 		return -EINVAL;
 	}
 
-	if (ipp_count) {
+	if (ipp_count || lcr_enable) {
 		/* get tfe csid IPP resource */
 		rc = cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(tfe_ctx,
-			in_port);
+			in_port, true, crop_enable);
+		if (rc) {
+			CAM_ERR(CAM_ISP,
+				"Acquire TFE CSID IPP resource Failed dual:%d",
+				in_port->usage_type);
+			goto err;
+		}
+	}
+
+	if (ppp_count) {
+		/* get ife csid PPP resource */
+		/* If both IPP and PPP paths are requested with the same vc dt
+		 * it is implied that the sensor is a type 3 PD sensor. Crop
+		 * must be enabled for this sensor on PPP path as well.
+		 */
+		if (!ipp_count)
+			crop_enable = false;
+
+		/* get tfe csid IPP resource */
+		rc = cam_tfe_hw_mgr_acquire_res_tfe_csid_pxl(tfe_ctx,
+				in_port, false, crop_enable);
 		if (rc) {
 			CAM_ERR(CAM_ISP,
 				"Acquire TFE CSID IPP resource Failed dual:%d",
@@ -1677,7 +1777,7 @@ static int cam_tfe_mgr_acquire_hw_for_ctx(
 		}
 	}
 
-	rc = cam_tfe_hw_mgr_acquire_res_tfe_in(tfe_ctx, in_port, pdaf_enable);
+	rc = cam_tfe_hw_mgr_acquire_res_tfe_in(tfe_ctx, in_port, pdaf_enable, lcr_enable);
 	if (rc) {
 		CAM_ERR(CAM_ISP,
 		"Acquire TFE IN resource Failed dual:%d", in_port->usage_type);
@@ -1694,6 +1794,7 @@ static int cam_tfe_mgr_acquire_hw_for_ctx(
 
 	*num_pix_port += ipp_count;
 	*num_rdi_port += rdi_count;
+	*num_pd_port  += ppp_count;
 
 	return 0;
 err:
@@ -2071,11 +2172,13 @@ static int cam_tfe_mgr_acquire_hw(void *hw_mgr_priv, void *acquire_hw_args)
 	struct cam_cdm_acquire_data         cdm_acquire;
 	uint32_t                            num_pix_port_per_in = 0;
 	uint32_t                            num_rdi_port_per_in = 0;
+	uint32_t                            num_pd_port_per_in = 0;
 	uint32_t                            pdaf_enable = 0;
 	uint32_t                            total_pix_port = 0;
 	uint32_t                            total_rdi_port = 0;
 	struct cam_isp_tfe_acquire_hw_info *acquire_hw_info = NULL;
 	uint32_t                            input_size = 0;
+	bool                                lcr_enable = false;
 
 	CAM_DBG(CAM_ISP, "Enter...");
 
@@ -2123,6 +2226,9 @@ static int cam_tfe_mgr_acquire_hw(void *hw_mgr_priv, void *acquire_hw_args)
 	tfe_ctx->cdm_ops = cdm_acquire.ops;
 	atomic_set(&tfe_ctx->cdm_done, 1);
 	tfe_ctx->last_cdm_done_req = 0;
+	tfe_ctx->current_mup = 0;
+	tfe_ctx->try_recovery_cnt = 0;
+	tfe_ctx->recovery_req_id = 0;
 
 	acquire_hw_info = (struct cam_isp_tfe_acquire_hw_info *)
 		acquire_args->acquire_info;
@@ -2161,6 +2267,21 @@ static int cam_tfe_mgr_acquire_hw(void *hw_mgr_priv, void *acquire_hw_args)
 		if (in_port[i].usage_type)
 			tfe_ctx->is_dual = true;
 
+	for (i = 0; i < acquire_hw_info->num_inputs; i++) {
+		cam_tfe_hw_mgr_preprocess_port(tfe_ctx, &in_port[i], &num_pix_port_per_in,
+			&num_rdi_port_per_in, &num_pd_port_per_in, &pdaf_enable, &lcr_enable);
+		total_pix_port += num_pix_port_per_in;
+		total_rdi_port += num_rdi_port_per_in;
+	}
+
+	/* Check whether context has only RDI resource */
+	if (!total_pix_port) {
+		tfe_ctx->is_rdi_only_context = 1;
+		CAM_DBG(CAM_ISP, "RDI only context");
+	} else {
+		tfe_ctx->is_rdi_only_context = 0;
+	}
+
 	/* acquire HW resources */
 	for (i = 0; i < acquire_hw_info->num_inputs; i++) {
 
@@ -2171,12 +2292,13 @@ static int cam_tfe_mgr_acquire_hw(void *hw_mgr_priv, void *acquire_hw_args)
 			goto free_cdm;
 		}
 
+		num_pix_port_per_in = 0;
+		num_rdi_port_per_in = 0;
+
 		CAM_DBG(CAM_ISP, "in_res_id %x", in_port[i].res_id);
 		rc = cam_tfe_mgr_acquire_hw_for_ctx(tfe_ctx, &in_port[i],
-			&num_pix_port_per_in, &num_rdi_port_per_in,
+			&num_pix_port_per_in, &num_rdi_port_per_in, &num_pd_port_per_in,
 			&pdaf_enable);
-		total_pix_port += num_pix_port_per_in;
-		total_rdi_port += num_rdi_port_per_in;
 
 		if (rc) {
 			CAM_ERR(CAM_ISP, "can not acquire resource");
@@ -2184,13 +2306,6 @@ static int cam_tfe_mgr_acquire_hw(void *hw_mgr_priv, void *acquire_hw_args)
 		}
 	}
 
-	/* Check whether context has only RDI resource */
-	if (!total_pix_port) {
-		tfe_ctx->is_rdi_only_context = 1;
-		CAM_DBG(CAM_ISP, "RDI only context");
-	} else
-		tfe_ctx->is_rdi_only_context = 0;
-
 	/* Process base info */
 	rc = cam_tfe_mgr_process_base_info(tfe_ctx);
 	if (rc) {
@@ -2327,6 +2442,7 @@ static int cam_tfe_mgr_acquire_dev(void *hw_mgr_priv, void *acquire_hw_args)
 	struct cam_cdm_acquire_data        cdm_acquire;
 	uint32_t                           num_pix_port_per_in = 0;
 	uint32_t                           num_rdi_port_per_in = 0;
+	uint32_t                           num_pd_port_per_in = 0;
 	uint32_t                           pdad_enable         = 0;
 	uint32_t                           total_pix_port = 0;
 	uint32_t                           total_rdi_port = 0;
@@ -2378,6 +2494,7 @@ static int cam_tfe_mgr_acquire_dev(void *hw_mgr_priv, void *acquire_hw_args)
 	tfe_ctx->cdm_ops = cdm_acquire.ops;
 	atomic_set(&tfe_ctx->cdm_done, 1);
 	tfe_ctx->last_cdm_done_req = 0;
+	tfe_ctx->current_mup = 0;
 
 	isp_resource = (struct cam_isp_resource *)acquire_args->acquire_info;
 
@@ -2446,7 +2563,7 @@ static int cam_tfe_mgr_acquire_dev(void *hw_mgr_priv, void *acquire_hw_args)
 
 			rc = cam_tfe_mgr_acquire_hw_for_ctx(tfe_ctx,
 				&gen_in_port[i],
-				&num_pix_port_per_in, &num_rdi_port_per_in,
+				&num_pix_port_per_in, &num_rdi_port_per_in, &num_pd_port_per_in,
 				&pdad_enable);
 			total_pix_port += num_pix_port_per_in;
 			total_rdi_port += num_rdi_port_per_in;
@@ -2561,7 +2678,8 @@ static int cam_tfe_classify_vote_info(
 {
 	int                                   rc = 0, i, j = 0;
 
-	if (hw_mgr_res->res_id == CAM_ISP_HW_TFE_IN_CAMIF) {
+	if ((hw_mgr_res->res_id == CAM_ISP_HW_TFE_IN_CAMIF) ||
+		(hw_mgr_res->res_id == CAM_ISP_HW_TFE_IN_PDLIB)) {
 		if (split_idx == CAM_ISP_HW_SPLIT_LEFT) {
 			if (*camif_l_bw_updated)
 				return rc;
@@ -2749,8 +2867,27 @@ static int cam_tfe_mgr_config_hw(void *hw_mgr_priv,
 		CAM_ERR(CAM_ISP, "Invalid context parameters");
 		return -EPERM;
 	}
-	if (atomic_read(&ctx->overflow_pending))
+	if (atomic_read(&ctx->overflow_pending)) {
+		CAM_DBG(CAM_ISP,
+			"Ctx[%pK][%d] Overflow pending, cannot apply req %llu",
+			ctx, ctx->ctx_index, cfg->request_id);
 		return -EINVAL;
+	}
+
+
+	/*
+	 * Assuming overflow recovery happens on req N, and we may
+	 * haven't got all the result for req N while apply N + 1,
+	 * so we reset try_recovery_cnt while apply N + 2.
+	 */
+	if (ctx->try_recovery_cnt &&
+		(cfg->request_id > (ctx->recovery_req_id + 1))) {
+		ctx->try_recovery_cnt = 0;
+		ctx->recovery_req_id = 0;
+		CAM_DBG(CAM_ISP,
+			"Ctx[%pK][%d] Reset try_recovery count for req %llu",
+			ctx, ctx->ctx_index, cfg->request_id);
+	}
 
 	hw_update_data = (struct cam_isp_prepare_hw_update_data  *) cfg->priv;
 	hw_update_data->isp_mgr_ctx = ctx;
@@ -2923,7 +3060,7 @@ static int cam_tfe_mgr_config_hw(void *hw_mgr_priv,
 		ctx->last_submit_bl_cmd.cmd[i].input_len = cdm_cmd->cmd[i].len;
 	}
 
-	if (!cfg->init_packet)
+	if (!cfg->init_packet && !hw_update_data->mup_en)
 		goto end;
 
 	for (i = 0; i < CAM_TFE_HW_CONFIG_WAIT_MAX_TRY; i++) {
@@ -2964,6 +3101,8 @@ static int cam_tfe_mgr_config_hw(void *hw_mgr_priv,
 			goto end;
 		} else {
 			rc = 0;
+			if (hw_update_data->mup_en)
+				ctx->current_mup = hw_update_data->mup_val;
 			CAM_DBG(CAM_ISP,
 				"config done Success for req_id=%llu ctx_index %d",
 				cfg->request_id, ctx->ctx_index);
@@ -3187,6 +3326,8 @@ static int cam_tfe_mgr_stop_hw(void *hw_mgr_priv, void *stop_hw_args)
 	cam_common_wait_for_completion_timeout(&ctx->config_done_complete,
 		msecs_to_jiffies(5));
 
+	ctx->current_mup = 0;
+
 	if (stop_isp->stop_only)
 		goto end;
 
@@ -3616,6 +3757,7 @@ static int cam_tfe_mgr_dump(void *hw_mgr_priv, void *args)
 				break;
 
 			case CAM_TFE_CSID_PATH_RES_IPP:
+			case CAM_TFE_CSID_PATH_RES_PPP:
 				if (hw_intf->hw_ops.process_cmd) {
 					rc = hw_intf->hw_ops.process_cmd(
 						hw_intf->hw_priv,
@@ -3654,6 +3796,7 @@ static int cam_tfe_mgr_dump(void *hw_mgr_priv, void *args)
 				break;
 
 			case CAM_ISP_HW_TFE_IN_CAMIF:
+			case CAM_ISP_HW_TFE_IN_PDLIB:
 				if (hw_intf->hw_ops.process_cmd) {
 					rc = hw_intf->hw_ops.process_cmd(
 						hw_intf->hw_priv,
@@ -3779,6 +3922,9 @@ static int cam_tfe_mgr_release_hw(void *hw_mgr_priv,
 	}
 	ctx->last_submit_bl_cmd.bl_count = 0;
 	ctx->packet = NULL;
+	ctx->current_mup = 0;
+	ctx->try_recovery_cnt = 0;
+	ctx->recovery_req_id = 0;
 
 	CAM_DBG(CAM_ISP, "Exit...ctx id:%d",
 		ctx->ctx_index);
@@ -3963,7 +4109,8 @@ static int cam_isp_tfe_blob_clock_update(
 			if (!hw_mgr_res->hw_res[i])
 				continue;
 
-			if (hw_mgr_res->res_id == CAM_ISP_HW_TFE_IN_CAMIF) {
+			if ((hw_mgr_res->res_id == CAM_ISP_HW_TFE_IN_CAMIF) ||
+				(hw_mgr_res->res_id == CAM_ISP_HW_TFE_IN_PDLIB)) {
 				if (i == CAM_ISP_HW_SPLIT_LEFT) {
 					if (camif_l_clk_updated)
 						continue;
@@ -4380,6 +4527,30 @@ static int cam_isp_tfe_packet_generic_blob_handler(void *user_data,
 			CAM_ERR(CAM_ISP, "BW limit update failed for TFE rc: %d", rc);
 	}
 		break;
+	case CAM_ISP_TFE_GENERIC_BLOB_TYPE_DYNAMIC_MODE_SWITCH: {
+		struct cam_isp_mode_switch_info         *mup_config;
+		struct cam_isp_prepare_hw_update_data   *prepare_hw_data;
+
+		if (blob_size < sizeof(struct cam_isp_mode_switch_info)) {
+			CAM_ERR(CAM_ISP, "Invalid blob size %u expected %lu",
+				blob_size,
+				sizeof(struct cam_isp_mode_switch_info));
+			return -EINVAL;
+		}
+
+		mup_config = (struct cam_isp_mode_switch_info *)blob_data;
+		CAM_DBG(CAM_ISP,
+			"Ctx id %d request id %lld csid mup value=%u num_exposures=%d",
+			tfe_mgr_ctx->ctx_index, prepare->packet->header.request_id,
+			mup_config->mup, mup_config->num_expoures);
+
+		prepare_hw_data = (struct cam_isp_prepare_hw_update_data *)prepare->priv;
+
+		prepare_hw_data->mup_en = true;
+		prepare_hw_data->mup_val = mup_config->mup;
+		prepare_hw_data->num_exp = mup_config->num_expoures;
+	}
+		break;
 	default:
 		CAM_WARN(CAM_ISP, "Invalid blob type %d", blob_type);
 		break;
@@ -4678,6 +4849,7 @@ static int cam_tfe_mgr_prepare_hw_update(void *hw_mgr_priv,
 	struct cam_isp_change_base_args          change_base_info = {0};
 	struct cam_isp_check_io_cfg_for_scratch  check_for_scratch = {0};
 	struct cam_isp_io_buf_info               io_buf_info = {0};
+	struct cam_isp_mode_switch_data          mup_config;
 
 	if (!hw_mgr_priv || !prepare_hw_update_args) {
 		CAM_ERR(CAM_ISP, "Invalid args");
@@ -4840,9 +5012,13 @@ static int cam_tfe_mgr_prepare_hw_update(void *hw_mgr_priv,
 			goto end;
 		}
 
+		mup_config.mup = prepare_hw_data->mup_val;
+		mup_config.num_expoures = prepare_hw_data->num_exp;
+		mup_config.mup_en = prepare_hw_data->mup_en;
+
 		/*Add reg update */
 		rc = cam_isp_add_reg_update(prepare, &ctx->res_list_tfe_in,
-			ctx->base[i].idx, &prepare_hw_data->kmd_cmd_buff_info, false);
+			ctx->base[i].idx, &prepare_hw_data->kmd_cmd_buff_info, false, &mup_config);
 		if (rc) {
 			CAM_ERR(CAM_ISP,
 				"Add Reg_update cmd Failed i=%d, idx=%d, rc=%d",
@@ -5016,6 +5192,58 @@ static void cam_tfe_mgr_pf_dump(uint32_t res_id,
 	}
 }
 
+static int cam_tfe_mgr_prog_default_settings(struct cam_tfe_hw_mgr_ctx *ctx)
+{
+	int rc = 0, i;
+	struct cam_isp_hw_mgr_res       *hw_mgr_res;
+	struct cam_isp_resource_node    *res;
+	struct list_head                *res_list;
+	struct cam_isp_hw_get_cmd_update    rup_args;
+	struct cam_isp_mode_switch_data     mup_config;
+
+
+	res_list = &ctx->res_list_tfe_in;
+
+	list_for_each_entry(hw_mgr_res, &ctx->res_list_tfe_in, list) {
+		if (hw_mgr_res->res_type != CAM_ISP_RESOURCE_TFE_IN)
+			continue;
+
+		for (i = 0; i < CAM_ISP_HW_SPLIT_MAX; i++) {
+			if (!hw_mgr_res->hw_res[i])
+				continue;
+
+			rup_args.res = hw_mgr_res->hw_res[i];
+			rup_args.cmd.cmd_buf_addr = NULL;
+			rup_args.cmd.size = 0;
+			rup_args.cmd_type = CAM_ISP_HW_CMD_GET_REG_UPDATE;
+			rup_args.reg_write = true;
+
+			mup_config.mup = ctx->current_mup;
+
+			rup_args.data = &mup_config;
+
+			res = rup_args.res;
+			rc = res->hw_intf->hw_ops.process_cmd(
+				res->hw_intf->hw_priv,
+				CAM_ISP_HW_CMD_GET_REG_UPDATE, &rup_args,
+				sizeof(struct cam_isp_hw_get_cmd_update));
+
+			if (rc) {
+				CAM_ERR(CAM_ISP, "failed for TFE: %d mup: %d ctx id:%d",
+					res->hw_intf->hw_idx, ctx->current_mup, ctx->ctx_index);
+				return rc;
+			}
+
+			CAM_DBG(CAM_ISP,
+				"Reg update for TFE: %d mup: %d ctx id:%d",
+				res->hw_intf->hw_idx, ctx->current_mup, ctx->ctx_index);
+		}
+
+	}
+
+	return rc;
+}
+
 static void cam_tfe_mgr_dump_pf_data(
 	struct cam_tfe_hw_mgr  *hw_mgr,
 	struct cam_hw_cmd_args *hw_cmd_args)
@@ -5232,6 +5460,9 @@ static int cam_tfe_mgr_cmd(void *hw_mgr_priv, void *cmd_args)
 				sizeof(struct cam_tfe_hw_comp_record) *
 				CAM_TFE_BUS_COMP_NUM_MAX);
 			break;
+		case CAM_ISP_HW_MGR_CMD_PROG_DEFAULT_CFG:
+			rc = cam_tfe_mgr_prog_default_settings(ctx);
+			break;
 		case CAM_ISP_HW_MGR_GET_SOF_TS:
 			rc = cam_tfe_mgr_cmd_get_sof_timestamp(ctx,
 				&isp_hw_cmd_args->u.sof_ts.curr,
@@ -5780,6 +6011,13 @@ static int cam_tfe_hw_mgr_handle_hw_err(
 		return rc;
 	}
 
+	if (ctx)
+		tfe_hw_mgr_ctx = (struct cam_tfe_hw_mgr_ctx *)ctx;
+	else {
+		CAM_ERR(CAM_ISP, "tfe hw mgr ctx NULL");
+		return rc;
+	}
+
 	err_evt_info = (struct cam_isp_hw_error_event_info *)event_info->event_data;
 	if (err_evt_info->err_type == CAM_TFE_IRQ_STATUS_VIOLATION)
 		error_event_data.error_type = CAM_ISP_HW_ERROR_VIOLATION;
@@ -5788,6 +6026,23 @@ static int cam_tfe_hw_mgr_handle_hw_err(
 		error_event_data.error_type = CAM_ISP_HW_ERROR_OVERFLOW;
 	else if (event_info->res_type == CAM_ISP_RESOURCE_TFE_OUT)
 		error_event_data.error_type = CAM_ISP_HW_ERROR_BUSIF_OVERFLOW;
+	else if (err_evt_info->err_type == CAM_TFE_IRQ_STATUS_OUT_OF_SYNC) {
+		error_event_data.error_type = CAM_ISP_HW_ERROR_CSID_SENSOR_FRAME_DROP;
+		if (tfe_hw_mgr_ctx->try_recovery_cnt < MAX_TFE_INTERNAL_RECOVERY_ATTEMPTS) {
+			error_event_data.try_internal_recovery = true;
+			if (!atomic_read(&tfe_hw_mgr_ctx->overflow_pending))
+				tfe_hw_mgr_ctx->try_recovery_cnt++;
+
+			if (!tfe_hw_mgr_ctx->recovery_req_id)
+				tfe_hw_mgr_ctx->recovery_req_id = tfe_hw_mgr_ctx->applied_req_id;
+		}
+
+		CAM_INFO(CAM_ISP,
+			"TFE: %u error: %u current_recovery_cnt: %u  recovery_req: %llu on ctx: %u",
+			event_info->hw_idx, error_event_data.error_type,
+			tfe_hw_mgr_ctx->try_recovery_cnt, tfe_hw_mgr_ctx->recovery_req_id,
+			tfe_hw_mgr_ctx->ctx_index);
+	}
 
 	spin_lock(&g_tfe_hw_mgr.ctx_lock);
 	if (err_evt_info->err_type == CAM_ISP_HW_ERROR_CSID_FATAL) {
@@ -5796,14 +6051,13 @@ static int cam_tfe_hw_mgr_handle_hw_err(
 		return rc;
 	}
 
-	if (ctx) {
-		tfe_hw_mgr_ctx =
-			(struct cam_tfe_hw_mgr_ctx *)ctx;
-		if ((event_info->res_type == CAM_ISP_RESOURCE_TFE_IN)
-			&& (!tfe_hw_mgr_ctx->is_rdi_only_context)
-			&& (event_info->res_id != CAM_ISP_HW_TFE_IN_CAMIF))
-			cam_tfe_hw_mgr_handle_hw_dump_info(tfe_hw_mgr_ctx, event_info);
-	}
+	if (event_info->res_type ==
+		CAM_ISP_RESOURCE_TFE_IN &&
+		!tfe_hw_mgr_ctx->is_rdi_only_context &&
+		event_info->res_id !=
+		CAM_ISP_HW_TFE_IN_CAMIF)
+		cam_tfe_hw_mgr_handle_hw_dump_info(
+			tfe_hw_mgr_ctx, event_info);
 
 	core_idx = event_info->hw_idx;
 
@@ -5822,7 +6076,7 @@ static int cam_tfe_hw_mgr_handle_hw_err(
 		return rc;
 	}
 
-	if (g_tfe_hw_mgr.debug_cfg.enable_recovery) {
+	if (!error_event_data.try_internal_recovery && g_tfe_hw_mgr.debug_cfg.enable_recovery) {
 		/* Trigger for recovery */
 		if (err_evt_info->err_type == CAM_TFE_IRQ_STATUS_VIOLATION)
 			recovery_data.error_type = CAM_ISP_HW_ERROR_VIOLATION;
@@ -5830,9 +6084,13 @@ static int cam_tfe_hw_mgr_handle_hw_err(
 			recovery_data.error_type = CAM_ISP_HW_ERROR_OVERFLOW;
 		cam_tfe_hw_mgr_do_error_recovery(&recovery_data);
 	} else {
-		CAM_DBG(CAM_ISP, "recovery is not enabled");
+		CAM_DBG(CAM_ISP, "recovery enabled: %d, internal_recovery: %d, ctx: %d",
+			error_event_data.try_internal_recovery,
+			g_tfe_hw_mgr.debug_cfg.enable_recovery,
+			tfe_hw_mgr_ctx->ctx_index);
 		rc = 0;
 	}
+
 end:
 	spin_unlock(&g_tfe_hw_mgr.ctx_lock);
 	return rc;
@@ -5873,6 +6131,8 @@ static int cam_tfe_hw_mgr_handle_hw_rup(
 			CAM_ISP_HW_EVENT_REG_UPDATE, (void *)&rup_event_data);
 		break;
 
+	case CAM_ISP_HW_TFE_IN_PDLIB:
+		break;
 	default:
 		CAM_ERR_RATE_LIMIT(CAM_ISP, "Invalid res_id: %d",
 			event_info->res_id);
@@ -5908,6 +6168,7 @@ static int cam_tfe_hw_mgr_handle_hw_epoch(
 	case CAM_ISP_HW_TFE_IN_RDI0:
 	case CAM_ISP_HW_TFE_IN_RDI1:
 	case CAM_ISP_HW_TFE_IN_RDI2:
+	case CAM_ISP_HW_TFE_IN_PDLIB:
 		break;
 
 	default:
@@ -5960,6 +6221,8 @@ static int cam_tfe_hw_mgr_handle_hw_sof(
 			CAM_ISP_HW_EVENT_SOF, (void *)&sof_done_event_data);
 		break;
 
+	case CAM_ISP_HW_TFE_IN_PDLIB:
+		break;
 	default:
 		CAM_ERR_RATE_LIMIT(CAM_ISP, "Invalid res_id: %d",
 			event_info->res_id);
@@ -6002,6 +6265,9 @@ static int cam_tfe_hw_mgr_handle_hw_eof(
 			CAM_ISP_HW_EVENT_EOF, (void *)&eof_done_event_data);
 		break;
 
+	case CAM_ISP_HW_TFE_IN_PDLIB:
+		break;
+
 	default:
 		CAM_ERR_RATE_LIMIT(CAM_ISP, "Invalid res_id: %d",
 			event_info->res_id);
@@ -6244,11 +6510,13 @@ int cam_tfe_hw_mgr_init(struct cam_hw_mgr_intf *hw_mgr_intf, int *iommu_hdl)
 	struct cam_iommu_handle cdm_handles;
 	struct cam_tfe_hw_mgr_ctx *ctx_pool;
 	struct cam_isp_hw_mgr_res *res_list_tfe_out;
+	struct cam_isp_hw_path_port_map path_port_map;
 	bool support_consumed_addr = false;
 
 	CAM_DBG(CAM_ISP, "Enter");
 
 	memset(&g_tfe_hw_mgr, 0, sizeof(g_tfe_hw_mgr));
+	memset(&path_port_map, 0, sizeof(path_port_map));
 
 	mutex_init(&g_tfe_hw_mgr.ctx_mutex);
 	spin_lock_init(&g_tfe_hw_mgr.ctx_lock);
@@ -6268,13 +6536,22 @@ int cam_tfe_hw_mgr_init(struct cam_hw_mgr_intf *hw_mgr_intf, int *iommu_hdl)
 				g_tfe_hw_mgr.tfe_devices[i]->hw_intf->hw_priv;
 			struct cam_hw_soc_info *soc_info = &tfe_hw->soc_info;
 
-			if (j == 0)
+			if (j == 0) {
 				tfe_device->hw_ops.process_cmd(
 					tfe_hw,
 					CAM_ISP_HW_CMD_IS_CONSUMED_ADDR_SUPPORT,
 					&support_consumed_addr,
 					sizeof(support_consumed_addr));
 
+				tfe_device->hw_ops.process_cmd(
+					tfe_hw,
+					CAM_ISP_HW_CMD_GET_PATH_PORT_MAP,
+					&path_port_map,
+					sizeof(struct cam_isp_hw_path_port_map));
+				CAM_DBG(CAM_ISP, "received %d path-port mappings",
+					path_port_map.num_entries);
+			}
+
 			j++;
 
 			g_tfe_hw_mgr.cdm_reg_map[i] = &soc_info->reg_map[0];
@@ -6292,6 +6569,13 @@ int cam_tfe_hw_mgr_init(struct cam_hw_mgr_intf *hw_mgr_intf, int *iommu_hdl)
 	}
 
 	g_tfe_hw_mgr.support_consumed_addr = support_consumed_addr;
+
+	for (i = 0; i < path_port_map.num_entries; i++) {
+		g_tfe_hw_mgr.path_port_map.entry[i][0] = path_port_map.entry[i][0];
+		g_tfe_hw_mgr.path_port_map.entry[i][1] = path_port_map.entry[i][1];
+	}
+	g_tfe_hw_mgr.path_port_map.num_entries = path_port_map.num_entries;
+
 	/* fill csid hw intf information */
 	for (i = 0, j = 0; i < CAM_TFE_CSID_HW_NUM_MAX; i++) {
 		rc = cam_tfe_csid_hw_init(&g_tfe_hw_mgr.csid_devices[i], i);

+ 8 - 0
drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.h

@@ -126,6 +126,9 @@ struct cam_tfe_cdm_user_data {
  * @bw_config_version          BW Config version
  * @tfe_bus_comp_grp          pointer to tfe comp group info
  * @cdm_userdata               CDM user data
+ * @try_recovery_cnt          Retry count for overflow recovery
+ * @current_mup               Current MUP val
+ * @recovery_req_id           The request id on which overflow recovery happens
  */
 struct cam_tfe_hw_mgr_ctx {
 	struct list_head                list;
@@ -170,6 +173,9 @@ struct cam_tfe_hw_mgr_ctx {
 	uint32_t                        bw_config_version;
 	struct cam_tfe_hw_comp_record  *tfe_bus_comp_grp;
 	struct cam_tfe_cdm_user_data    cdm_userdata;
+	uint32_t                        current_mup;
+	uint32_t                        try_recovery_cnt;
+	uint64_t                        recovery_req_id;
 };
 
 /**
@@ -190,6 +196,7 @@ struct cam_tfe_hw_mgr_ctx {
  * @tfe_dev_caps           tfe device capability per core
  * @work q                 work queue for TFE hw manager
  * @debug_cfg              debug configuration
+ * @path_port_map          Mapping of outport to TFE mux
  * @support_consumed_addr  indicate whether hw supports last consumed address
  * @ctx_lock               Spinlock for HW manager
  */
@@ -209,6 +216,7 @@ struct cam_tfe_hw_mgr {
 	struct cam_tfe_hw_get_hw_cap   tfe_dev_caps[CAM_TFE_HW_NUM_MAX];
 	struct cam_req_mgr_core_workq *workq;
 	struct cam_tfe_hw_mgr_debug    debug_cfg;
+	struct cam_isp_hw_path_port_map  path_port_map;
 	bool                           support_consumed_addr;
 	spinlock_t                     ctx_lock;
 };

+ 7 - 4
drivers/cam_isp/isp_hw_mgr/hw_utils/cam_isp_packet_parser.c

@@ -1242,12 +1242,13 @@ int cam_isp_add_reg_update(
 	struct list_head                     *res_list_isp_src,
 	uint32_t                              base_idx,
 	struct cam_kmd_buf_info              *kmd_buf_info,
-	bool                                  combine)
+	bool                                  combine,
+	void                                 *priv_data)
 {
 	int rc = -EINVAL;
-	struct cam_isp_resource_node         *res;
-	struct cam_isp_hw_mgr_res            *hw_mgr_res;
-	struct cam_isp_hw_get_cmd_update      get_regup;
+	struct cam_isp_resource_node            *res;
+	struct cam_isp_hw_mgr_res               *hw_mgr_res;
+	struct cam_isp_hw_get_cmd_update         get_regup;
 	uint32_t kmd_buf_remain_size, i, reg_update_size;
 
 	/* Max one hw entries required for each base */
@@ -1293,6 +1294,8 @@ int cam_isp_add_reg_update(
 			get_regup.cmd_type = CAM_ISP_HW_CMD_GET_REG_UPDATE;
 			get_regup.res = res;
 
+			get_regup.data = priv_data;
+
 			rc = res->hw_intf->hw_ops.process_cmd(
 				res->hw_intf->hw_priv,
 				CAM_ISP_HW_CMD_GET_REG_UPDATE, &get_regup,

+ 3 - 1
drivers/cam_isp/isp_hw_mgr/hw_utils/include/cam_isp_packet_parser.h

@@ -290,6 +290,7 @@ int cam_isp_add_io_buffers(struct cam_isp_io_buf_info   *io_info);
  * @base_idx:              Base or dev index of the IFE/VFE HW instance
  * @kmd_buf_info:          Kmd buffer to store the change base command
  * @combine:               Indicate whether combine with prev update entry
+ * @priv_data:             private data for HW driver
  * @return:                0 for success
  *                         -EINVAL for Fail
  */
@@ -298,7 +299,8 @@ int cam_isp_add_reg_update(
 	struct list_head                     *res_list_isp_src,
 	uint32_t                              base_idx,
 	struct cam_kmd_buf_info              *kmd_buf_info,
-	bool                                  combine);
+	bool                                  combine,
+	void                                 *priv_data);
 
 /*
  * cam_isp_add_comp_wait()

+ 15 - 0
drivers/cam_isp/isp_hw_mgr/include/cam_isp_hw_mgr_intf.h

@@ -546,6 +546,21 @@ struct cam_isp_lcr_rdi_cfg_args {
 	bool                           is_init;
 };
 
+
+/**
+ * struct cam_isp_mode_switch_data - isp hardware mode update arguments
+ *
+ * @mup                 Mup value
+ * @num_expoures        Number of exposures
+ * @mup_en              Flag to indicate if mup is enable
+ *
+ */
+struct cam_isp_mode_switch_data {
+	uint32_t                      mup;
+	uint32_t                      num_expoures;
+	bool                          mup_en;
+};
+
 /**
  * cam_isp_hw_mgr_init()
  *

+ 2 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_isp_hw.h

@@ -517,6 +517,7 @@ struct cam_isp_hw_fcg_cmd {
  * @cmd:             Command buffer information
  * @use_scratch_cfg: To indicate if it's scratch buffer config
  * @trigger_cdm_en:  Flag to indicate if cdm is trigger
+ * @reg_write:        if set use AHB to config rup/aup
  *
  */
 struct cam_isp_hw_get_cmd_update {
@@ -531,6 +532,7 @@ struct cam_isp_hw_get_cmd_update {
 		struct cam_isp_hw_get_wm_update      *rm_update;
 	};
 	bool trigger_cdm_en;
+	bool reg_write;
 };
 
 /*

+ 8 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_tfe_csid_hw_intf.h

@@ -23,6 +23,7 @@ enum cam_tfe_csid_path_res_id {
 	CAM_TFE_CSID_PATH_RES_RDI_1,
 	CAM_TFE_CSID_PATH_RES_RDI_2,
 	CAM_TFE_CSID_PATH_RES_IPP,
+	CAM_TFE_CSID_PATH_RES_PPP,
 	CAM_TFE_CSID_PATH_RES_MAX,
 };
 
@@ -36,6 +37,7 @@ enum cam_tfe_csid_irq_reg {
 	TFE_CSID_IRQ_REG_TOP,
 	TFE_CSID_IRQ_REG_RX,
 	TFE_CSID_IRQ_REG_IPP,
+	TFE_CSID_IRQ_REG_PPP,
 	TFE_CSID_IRQ_REG_MAX,
 };
 
@@ -96,19 +98,23 @@ struct cam_isp_tfe_in_port_generic_info {
  * struct cam_tfe_csid_hw_caps- get the CSID hw capability
  * @num_rdis:       number of rdis supported by CSID HW device
  * @num_pix:        number of pxl paths supported by CSID HW device
+ * @num_ppp:        number of ppp paths supported by CSID HW device
  * @major_version : major version
  * @minor_version:  minor version
  * @version_incr:   version increment
  * @sync_clk:       sync clocks such that freq(TFE)>freq(CSID)>freq(CSIPHY)
+ * @is_lite:        Indicate if it is CSID Lite
  *
  */
 struct cam_tfe_csid_hw_caps {
 	uint32_t      num_rdis;
 	uint32_t      num_pix;
+	uint32_t      num_ppp;
 	uint32_t      major_version;
 	uint32_t      minor_version;
 	uint32_t      version_incr;
 	bool          sync_clk;
+	bool          is_lite;
 };
 
 /**
@@ -126,6 +132,7 @@ struct cam_tfe_csid_hw_caps {
  * @event_cb_prv: Context data
  * @event_cb:     Callback function to hw mgr in case of hw events
  * @node_res :    Reserved resource structure pointer
+ * @crop_enable : Flag to indicate CSID crop enable
  *
  */
 struct cam_tfe_csid_hw_reserve_resource_args {
@@ -139,6 +146,7 @@ struct cam_tfe_csid_hw_reserve_resource_args {
 	void                                     *event_cb_prv;
 	cam_hw_mgr_event_cb_func                  event_cb;
 	struct cam_isp_resource_node             *node_res;
+	bool                                      crop_enable;
 };
 
 /**

+ 4 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_tfe_hw_intf.h

@@ -19,6 +19,7 @@ enum cam_isp_hw_tfe_in {
 	CAM_ISP_HW_TFE_IN_RDI0        = 1,
 	CAM_ISP_HW_TFE_IN_RDI1        = 2,
 	CAM_ISP_HW_TFE_IN_RDI2        = 3,
+	CAM_ISP_HW_TFE_IN_PDLIB       = 4,
 	CAM_ISP_HW_TFE_IN_MAX,
 };
 
@@ -35,6 +36,7 @@ enum cam_tfe_hw_irq_status {
 	CAM_TFE_IRQ_STATUS_OVERFLOW,
 	CAM_TFE_IRQ_STATUS_P2I_ERROR,
 	CAM_TFE_IRQ_STATUS_VIOLATION,
+	CAM_TFE_IRQ_STATUS_OUT_OF_SYNC,
 	CAM_TFE_IRQ_STATUS_MAX,
 };
 
@@ -120,6 +122,7 @@ struct cam_tfe_hw_tfe_out_acquire_args {
  * @in_port:                 Input port details to acquire
  * @camif_pd_enable          Camif pd enable or disable
  * @dual_tfe_sync_sel_idx    Dual tfe master hardware index
+ * @lcr_enable               LCR enable field
  */
 struct cam_tfe_hw_tfe_in_acquire_args {
 	struct cam_isp_resource_node            *rsrc_node;
@@ -129,6 +132,7 @@ struct cam_tfe_hw_tfe_in_acquire_args {
 	enum cam_isp_hw_sync_mode                sync_mode;
 	bool                                     camif_pd_enable;
 	uint32_t                                 dual_tfe_sync_sel_idx;
+	bool                                     lcr_enable;
 };
 
 /*

+ 11 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid.c

@@ -1,6 +1,7 @@
 // SPDX-License-Identifier: GPL-2.0-only
 /*
  * Copyright (c) 2021, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
  */
 
 
@@ -8,6 +9,8 @@
 #include "cam_tfe_csid_core.h"
 #include "cam_tfe_csid530.h"
 #include "cam_tfe_csid640.h"
+#include "cam_tfe_csid640_210.h"
+#include "cam_tfe_csid770.h"
 #include "cam_tfe_csid_dev.h"
 #include "camera_main.h"
 
@@ -22,6 +25,14 @@ static const struct of_device_id cam_tfe_csid_dt_match[] = {
 		.compatible = "qcom,csid640",
 		.data = &cam_tfe_csid640_hw_info,
 	},
+	{
+		.compatible = "qcom,csid640_210",
+		.data = &cam_tfe_csid640_210_hw_info,
+	},
+	{
+		.compatible = "qcom,csid770",
+		.data = &cam_tfe_csid770_hw_info,
+	},
 	{}
 };
 

+ 363 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid770.h

@@ -0,0 +1,363 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+/*
+ * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
+ */
+
+#ifndef _CAM_TFE_CSID_770_H_
+#define _CAM_TFE_CSID_770_H_
+
+#include "cam_tfe_csid_core.h"
+
+#define CAM_TFE_CSID_VERSION_V770                 0x70070000
+
+static struct cam_tfe_csid_pxl_reg_offset  cam_tfe_csid_770_ipp_reg_offset = {
+	.csid_pxl_irq_status_addr            = 0x30,
+	.csid_pxl_irq_mask_addr              = 0x34,
+	.csid_pxl_irq_clear_addr             = 0x38,
+	.csid_pxl_irq_set_addr               = 0x3c,
+
+	.csid_pxl_cfg0_addr                  = 0x200,
+	.csid_pxl_cfg1_addr                  = 0x204,
+	.csid_pxl_ctrl_addr                  = 0x208,
+	.csid_pxl_frame_drop_pattern         = 0x20c,
+	.csid_pxl_frame_drop_period          = 0x210,
+	.csid_pxl_irq_subsample_pattern      = 0x214,
+	.csid_pxl_irq_subsample_period       = 0x218,
+	.csid_pxl_hcrop_addr                 = 0x21c,
+	.csid_pxl_vcrop_addr                 = 0x220,
+	.csid_pxl_rst_strobes_addr           = 0x240,
+	.csid_pxl_status_addr                = 0x254,
+	.csid_pxl_misr_val_addr              = 0x258,
+	.csid_pxl_format_measure_cfg0_addr   = 0x270,
+	.csid_pxl_format_measure_cfg1_addr   = 0x274,
+	.csid_pxl_format_measure0_addr       = 0x278,
+	.csid_pxl_format_measure1_addr       = 0x27c,
+	.csid_pxl_format_measure2_addr       = 0x280,
+	.csid_pxl_timestamp_curr0_sof_addr   = 0x290,
+	.csid_pxl_timestamp_curr1_sof_addr   = 0x294,
+	.csid_pxl_timestamp_perv0_sof_addr   = 0x298,
+	.csid_pxl_timestamp_perv1_sof_addr   = 0x29c,
+	.csid_pxl_timestamp_curr0_eof_addr   = 0x2a0,
+	.csid_pxl_timestamp_curr1_eof_addr   = 0x2a4,
+	.csid_pxl_timestamp_perv0_eof_addr   = 0x2a8,
+	.csid_pxl_timestamp_perv1_eof_addr   = 0x2ac,
+	.csid_pxl_err_recovery_cfg0_addr     = 0x2d0,
+	.csid_pxl_err_recovery_cfg1_addr     = 0x2d4,
+	.csid_pxl_err_recovery_cfg2_addr     = 0x2d8,
+	.csid_pxl_multi_vcdt_cfg0_addr       = 0x2dc,
+
+	/* configurations */
+	.pix_store_en_shift_val              = 7,
+	.early_eof_en_shift_val              = 29,
+	.halt_master_sel_shift               = 4,
+	.halt_mode_shift                     = 2,
+	.halt_master_sel_master_val          = 3,
+	.halt_master_sel_slave_val           = 0,
+	.binning_supported                   = 3,
+	.bin_qcfa_en_shift_val               = 30,
+	.bin_en_shift_val                    = 2,
+	.is_multi_vc_dt_supported            = true,
+	.format_measure_en_shift_val         = 0,
+	.measure_en_hbi_vbi_cnt_val          = 0xc,
+};
+
+static struct cam_tfe_csid_pxl_reg_offset  cam_tfe_csid_770_ppp_reg_offset = {
+	.csid_pxl_irq_status_addr            = 0xA0,
+	.csid_pxl_irq_mask_addr              = 0xA4,
+	.csid_pxl_irq_clear_addr             = 0xA8,
+	.csid_pxl_irq_set_addr               = 0xAc,
+
+	.csid_pxl_cfg0_addr                  = 0x700,
+	.csid_pxl_cfg1_addr                  = 0x704,
+	.csid_pxl_ctrl_addr                  = 0x708,
+	.csid_pxl_frame_drop_pattern         = 0x70c,
+	.csid_pxl_frame_drop_period          = 0x710,
+	.csid_pxl_irq_subsample_pattern      = 0x714,
+	.csid_pxl_irq_subsample_period       = 0x718,
+	.csid_pxl_hcrop_addr                 = 0x71c,
+	.csid_pxl_vcrop_addr                 = 0x720,
+	.csid_pxl_rst_strobes_addr           = 0x740,
+	.csid_pxl_status_addr                = 0x754,
+	.csid_pxl_misr_val_addr              = 0x758,
+	.csid_pxl_format_measure_cfg0_addr   = 0x770,
+	.csid_pxl_format_measure_cfg1_addr   = 0x774,
+	.csid_pxl_format_measure0_addr       = 0x778,
+	.csid_pxl_format_measure1_addr       = 0x77c,
+	.csid_pxl_format_measure2_addr       = 0x780,
+	.csid_pxl_timestamp_curr0_sof_addr   = 0x790,
+	.csid_pxl_timestamp_curr1_sof_addr   = 0x794,
+	.csid_pxl_timestamp_perv0_sof_addr   = 0x798,
+	.csid_pxl_timestamp_perv1_sof_addr   = 0x79c,
+	.csid_pxl_timestamp_curr0_eof_addr   = 0x7a0,
+	.csid_pxl_timestamp_curr1_eof_addr   = 0x7a4,
+	.csid_pxl_timestamp_perv0_eof_addr   = 0x7a8,
+	.csid_pxl_timestamp_perv1_eof_addr   = 0x7ac,
+	.csid_pxl_ppp_sparse_pd_ext_cfg0     = 0x7c0,
+	.csid_pxl_err_recovery_cfg0_addr     = 0x7d0,
+	.csid_pxl_err_recovery_cfg1_addr     = 0x7d4,
+	.csid_pxl_err_recovery_cfg2_addr     = 0x7d8,
+	.csid_pxl_multi_vcdt_cfg0_addr       = 0x7dc,
+
+	/* configurations */
+	.pix_store_en_shift_val              = 7,
+	.early_eof_en_shift_val              = 29,
+	.halt_master_sel_shift               = 4,
+	.halt_mode_shift                     = 2,
+	.halt_master_sel_master_val          = 3,
+	.halt_master_sel_slave_val           = 0,
+	.binning_supported                   = 0,
+	.bin_qcfa_en_shift_val               = 30,
+	.bin_en_shift_val                    = 2,
+	.is_multi_vc_dt_supported            = true,
+	.format_measure_en_shift_val         = 0,
+	.measure_en_hbi_vbi_cnt_val          = 0xc,
+};
+
+static struct cam_tfe_csid_rdi_reg_offset cam_tfe_csid_770_rdi_0_reg_offset = {
+	.csid_rdi_irq_status_addr                 = 0x40,
+	.csid_rdi_irq_mask_addr                   = 0x44,
+	.csid_rdi_irq_clear_addr                  = 0x48,
+	.csid_rdi_irq_set_addr                    = 0x4c,
+
+	.csid_rdi_cfg0_addr                       = 0x300,
+	.csid_rdi_cfg1_addr                       = 0x304,
+	.csid_rdi_ctrl_addr                       = 0x308,
+	.csid_rdi_frame_drop_pattern              = 0x30c,
+	.csid_rdi_frame_drop_period               = 0x310,
+	.csid_rdi_irq_subsample_pattern           = 0x314,
+	.csid_rdi_irq_subsample_period            = 0x318,
+	.csid_rdi_rst_strobes_addr                = 0x340,
+	.csid_rdi_status_addr                     = 0x350,
+	.csid_rdi_misr_val0_addr                  = 0x354,
+	.csid_rdi_misr_val1_addr                  = 0x358,
+	.csid_rdi_misr_val2_addr                  = 0x35c,
+	.csid_rdi_misr_val3_addr                  = 0x360,
+	.csid_rdi_format_measure_cfg0_addr        = 0x370,
+	.csid_rdi_format_measure_cfg1_addr        = 0x374,
+	.csid_rdi_format_measure0_addr            = 0x378,
+	.csid_rdi_format_measure1_addr            = 0x37c,
+	.csid_rdi_format_measure2_addr            = 0x380,
+	.csid_rdi_timestamp_curr0_sof_addr        = 0x390,
+	.csid_rdi_timestamp_curr1_sof_addr        = 0x394,
+	.csid_rdi_timestamp_prev0_sof_addr        = 0x398,
+	.csid_rdi_timestamp_prev1_sof_addr        = 0x39c,
+	.csid_rdi_timestamp_curr0_eof_addr        = 0x3a0,
+	.csid_rdi_timestamp_curr1_eof_addr        = 0x3a4,
+	.csid_rdi_timestamp_prev0_eof_addr        = 0x3a8,
+	.csid_rdi_timestamp_prev1_eof_addr        = 0x3ac,
+	.csid_rdi_err_recovery_cfg0_addr          = 0x3b0,
+	.csid_rdi_err_recovery_cfg1_addr          = 0x3b4,
+	.csid_rdi_err_recovery_cfg2_addr          = 0x3b8,
+	.csid_rdi_byte_cntr_ping_addr             = 0x3e0,
+	.csid_rdi_byte_cntr_pong_addr             = 0x3e4,
+	.csid_rdi_multi_vcdt_cfg0_addr            = 0x3bc,
+
+	/* configurations */
+	.is_multi_vc_dt_supported                 = true,
+	.format_measure_en_shift_val              = 0,
+	.measure_en_hbi_vbi_cnt_val               = 0xc,
+};
+
+static struct cam_tfe_csid_rdi_reg_offset cam_tfe_csid_770_rdi_1_reg_offset = {
+	.csid_rdi_irq_status_addr                 = 0x50,
+	.csid_rdi_irq_mask_addr                   = 0x54,
+	.csid_rdi_irq_clear_addr                  = 0x58,
+	.csid_rdi_irq_set_addr                    = 0x5c,
+
+	.csid_rdi_cfg0_addr                       = 0x400,
+	.csid_rdi_cfg1_addr                       = 0x404,
+	.csid_rdi_ctrl_addr                       = 0x408,
+	.csid_rdi_frame_drop_pattern              = 0x40c,
+	.csid_rdi_frame_drop_period               = 0x410,
+	.csid_rdi_irq_subsample_pattern           = 0x414,
+	.csid_rdi_irq_subsample_period            = 0x418,
+	.csid_rdi_rst_strobes_addr                = 0x440,
+	.csid_rdi_status_addr                     = 0x450,
+	.csid_rdi_misr_val0_addr                  = 0x454,
+	.csid_rdi_misr_val1_addr                  = 0x458,
+	.csid_rdi_misr_val2_addr                  = 0x45c,
+	.csid_rdi_misr_val3_addr                  = 0x460,
+	.csid_rdi_format_measure_cfg0_addr        = 0x470,
+	.csid_rdi_format_measure_cfg1_addr        = 0x474,
+	.csid_rdi_format_measure0_addr            = 0x478,
+	.csid_rdi_format_measure1_addr            = 0x47c,
+	.csid_rdi_format_measure2_addr            = 0x480,
+	.csid_rdi_timestamp_curr0_sof_addr        = 0x490,
+	.csid_rdi_timestamp_curr1_sof_addr        = 0x494,
+	.csid_rdi_timestamp_prev0_sof_addr        = 0x498,
+	.csid_rdi_timestamp_prev1_sof_addr        = 0x49c,
+	.csid_rdi_timestamp_curr0_eof_addr        = 0x4a0,
+	.csid_rdi_timestamp_curr1_eof_addr        = 0x4a4,
+	.csid_rdi_timestamp_prev0_eof_addr        = 0x4a8,
+	.csid_rdi_timestamp_prev1_eof_addr        = 0x4ac,
+	.csid_rdi_err_recovery_cfg0_addr          = 0x4b0,
+	.csid_rdi_err_recovery_cfg1_addr          = 0x4b4,
+	.csid_rdi_err_recovery_cfg2_addr          = 0x4b8,
+	.csid_rdi_byte_cntr_ping_addr             = 0x4e0,
+	.csid_rdi_byte_cntr_pong_addr             = 0x4e4,
+	.csid_rdi_multi_vcdt_cfg0_addr            = 0x4bc,
+
+	/* configurations */
+	.is_multi_vc_dt_supported                 = true,
+	.format_measure_en_shift_val              = 0,
+	.measure_en_hbi_vbi_cnt_val               = 0xc,
+};
+
+static struct cam_tfe_csid_rdi_reg_offset cam_tfe_csid_770_rdi_2_reg_offset = {
+	.csid_rdi_irq_status_addr                 = 0x60,
+	.csid_rdi_irq_mask_addr                   = 0x64,
+	.csid_rdi_irq_clear_addr                  = 0x68,
+	.csid_rdi_irq_set_addr                    = 0x6c,
+
+	.csid_rdi_cfg0_addr                       = 0x500,
+	.csid_rdi_cfg1_addr                       = 0x504,
+	.csid_rdi_ctrl_addr                       = 0x508,
+	.csid_rdi_frame_drop_pattern              = 0x50c,
+	.csid_rdi_frame_drop_period               = 0x510,
+	.csid_rdi_irq_subsample_pattern           = 0x514,
+	.csid_rdi_irq_subsample_period            = 0x518,
+	.csid_rdi_rst_strobes_addr                = 0x540,
+	.csid_rdi_status_addr                     = 0x550,
+	.csid_rdi_misr_val0_addr                  = 0x554,
+	.csid_rdi_misr_val1_addr                  = 0x558,
+	.csid_rdi_misr_val2_addr                  = 0x55c,
+	.csid_rdi_misr_val3_addr                  = 0x560,
+	.csid_rdi_format_measure_cfg0_addr        = 0x570,
+	.csid_rdi_format_measure_cfg1_addr        = 0x574,
+	.csid_rdi_format_measure0_addr            = 0x578,
+	.csid_rdi_format_measure1_addr            = 0x57c,
+	.csid_rdi_format_measure2_addr            = 0x580,
+	.csid_rdi_timestamp_curr0_sof_addr        = 0x590,
+	.csid_rdi_timestamp_curr1_sof_addr        = 0x594,
+	.csid_rdi_timestamp_prev0_sof_addr        = 0x598,
+	.csid_rdi_timestamp_prev1_sof_addr        = 0x59c,
+	.csid_rdi_timestamp_curr0_eof_addr        = 0x5a0,
+	.csid_rdi_timestamp_curr1_eof_addr        = 0x5a4,
+	.csid_rdi_timestamp_prev0_eof_addr        = 0x5a8,
+	.csid_rdi_timestamp_prev1_eof_addr        = 0x5ac,
+	.csid_rdi_err_recovery_cfg0_addr          = 0x5b0,
+	.csid_rdi_err_recovery_cfg1_addr          = 0x5b4,
+	.csid_rdi_err_recovery_cfg2_addr          = 0x5b8,
+	.csid_rdi_byte_cntr_ping_addr             = 0x5e0,
+	.csid_rdi_byte_cntr_pong_addr             = 0x5e4,
+	.csid_rdi_multi_vcdt_cfg0_addr            = 0x5bc,
+
+	/* configurations */
+	.is_multi_vc_dt_supported                 = true,
+	.format_measure_en_shift_val              = 0,
+	.measure_en_hbi_vbi_cnt_val               = 0xc,
+};
+
+static struct cam_tfe_csid_csi2_rx_reg_offset
+	cam_tfe_csid_770_csi2_reg_offset = {
+	.csid_csi2_rx_irq_status_addr                 = 0x20,
+	.csid_csi2_rx_irq_mask_addr                   = 0x24,
+	.csid_csi2_rx_irq_clear_addr                  = 0x28,
+	.csid_csi2_rx_irq_set_addr                    = 0x2c,
+
+	/*CSI2 rx control */
+	.phy_sel_base                                 = 1,
+	.csid_csi2_rx_cfg0_addr                       = 0x100,
+	.csid_csi2_rx_cfg1_addr                       = 0x104,
+	.csid_csi2_rx_capture_ctrl_addr               = 0x108,
+	.csid_csi2_rx_rst_strobes_addr                = 0x110,
+	.csid_csi2_rx_cap_unmap_long_pkt_hdr_0_addr   = 0x120,
+	.csid_csi2_rx_cap_unmap_long_pkt_hdr_1_addr   = 0x124,
+	.csid_csi2_rx_captured_short_pkt_0_addr       = 0x128,
+	.csid_csi2_rx_captured_short_pkt_1_addr       = 0x12c,
+	.csid_csi2_rx_captured_long_pkt_0_addr        = 0x130,
+	.csid_csi2_rx_captured_long_pkt_1_addr        = 0x134,
+	.csid_csi2_rx_captured_long_pkt_ftr_addr      = 0x138,
+	.csid_csi2_rx_captured_cphy_pkt_hdr_addr      = 0x13c,
+	.csid_csi2_rx_total_pkts_rcvd_addr            = 0x160,
+	.csid_csi2_rx_stats_ecc_addr                  = 0x164,
+	.csid_csi2_rx_total_crc_err_addr              = 0x168,
+
+	.phy_tpg_base_id                              = 0,
+	.csi2_rst_srb_all                             = 0x3FFF,
+	.csi2_rst_done_shift_val                      = 27,
+	.csi2_irq_mask_all                            = 0xFFFFFFF,
+	.csi2_misr_enable_shift_val                   = 6,
+	.csi2_capture_long_pkt_en_shift               = 0,
+	.csi2_capture_short_pkt_en_shift              = 1,
+	.csi2_capture_cphy_pkt_en_shift               = 2,
+	.csi2_capture_long_pkt_dt_shift               = 4,
+	.csi2_capture_long_pkt_vc_shift               = 10,
+	.csi2_capture_short_pkt_vc_shift              = 12,
+	.csi2_capture_cphy_pkt_dt_shift               = 14,
+	.csi2_capture_cphy_pkt_vc_shift               = 20,
+	.csi2_rx_phy_num_mask                         = 0x7,
+	.csi2_rx_long_pkt_hdr_rst_stb_shift           = 0x1,
+	.csi2_rx_short_pkt_hdr_rst_stb_shift          = 0x2,
+	.csi2_rx_cphy_pkt_hdr_rst_stb_shift           = 0x3,
+};
+
+static struct cam_tfe_csid_common_reg_offset
+	cam_tfe_csid_770_cmn_reg_offset = {
+	.csid_hw_version_addr                         = 0x0,
+	.csid_cfg0_addr                               = 0x4,
+	.csid_ctrl_addr                               = 0x8,
+	.csid_rst_strobes_addr                        = 0x10,
+
+	.csid_test_bus_ctrl_addr                      = 0x14,
+	.csid_top_irq_status_addr                     = 0x70,
+	.csid_top_irq_mask_addr                       = 0x74,
+	.csid_top_irq_clear_addr                      = 0x78,
+	.csid_top_irq_set_addr                        = 0x7c,
+	.csid_irq_cmd_addr                            = 0x80,
+
+	/*configurations */
+	.major_version                                = 5,
+	.minor_version                                = 3,
+	.version_incr                                 = 0,
+	.num_rdis                                     = 3,
+	.num_pix                                      = 1,
+	.num_ppp                                      = 1,
+	.csid_reg_rst_stb                             = 1,
+	.csid_rst_stb                                 = 0x1e,
+	.csid_rst_stb_sw_all                          = 0x1f,
+	.ipp_path_rst_stb_all                         = 0x17,
+	.ppp_path_rst_stb_all                         = 0x17,
+	.rdi_path_rst_stb_all                         = 0x97,
+	.path_rst_done_shift_val                      = 1,
+	.path_en_shift_val                            = 31,
+	.dt_id_shift_val                              = 27,
+	.vc_shift_val                                 = 22,
+	.dt_shift_val                                 = 16,
+	.vc1_shift_val                                = 2,
+	.dt1_shift_val                                = 7,
+	.multi_vc_dt_en_shift_val                     = 0,
+	.fmt_shift_val                                = 12,
+	.plain_fmt_shit_val                           = 10,
+	.crop_v_en_shift_val                          = 6,
+	.crop_h_en_shift_val                          = 5,
+	.crop_shift                                   = 16,
+	.ipp_irq_mask_all                             = 0x3FFFF,
+	.ppp_irq_mask_all                             = 0x3FFFF,
+	.rdi_irq_mask_all                             = 0x3FFFF,
+	.top_tfe2_pix_pipe_fuse_reg                   = 0xFE4,
+	.top_tfe2_fuse_reg                            = 0xFE8,
+	.format_measure_support                       = true,
+	.format_measure_height_shift_val              = 16,
+	.format_measure_height_mask_val               = 0xe,
+	.format_measure_width_mask_val                = 0x10,
+};
+
+static struct cam_tfe_csid_reg_offset cam_tfe_csid_770_reg_offset = {
+	.cmn_reg          = &cam_tfe_csid_770_cmn_reg_offset,
+	.csi2_reg         = &cam_tfe_csid_770_csi2_reg_offset,
+	.ipp_reg          = &cam_tfe_csid_770_ipp_reg_offset,
+	.ppp_reg          = &cam_tfe_csid_770_ppp_reg_offset,
+	.rdi_reg = {
+		&cam_tfe_csid_770_rdi_0_reg_offset,
+		&cam_tfe_csid_770_rdi_1_reg_offset,
+		&cam_tfe_csid_770_rdi_2_reg_offset,
+		},
+};
+
+static struct cam_tfe_csid_hw_info cam_tfe_csid770_hw_info = {
+	.csid_reg = &cam_tfe_csid_770_reg_offset,
+	.hw_dts_version = CAM_TFE_CSID_VERSION_V770,
+};
+
+#endif /*_CAM_TFE_CSID_770_H_ */

+ 486 - 25
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_core.c

@@ -47,7 +47,7 @@
 /* Max CSI Rx irq error count threshold value */
 #define CAM_TFE_CSID_MAX_IRQ_ERROR_COUNT               5
 
-static int cam_tfe_csid_is_ipp_format_supported(
+static int cam_tfe_csid_is_ipp_ppp_format_supported(
 	uint32_t in_format)
 {
 	int rc = -EINVAL;
@@ -170,7 +170,7 @@ static int cam_tfe_csid_get_format_rdi(
 	return rc;
 }
 
-static int cam_tfe_csid_get_format_ipp(
+static int cam_tfe_csid_get_format_ipp_ppp(
 	uint32_t in_format,
 	uint32_t *decode_fmt, uint32_t *plain_fmt)
 {
@@ -341,6 +341,17 @@ static bool cam_tfe_csid_check_path_active(struct cam_tfe_csid_hw   *csid_hw)
 			goto end;
 	}
 
+	/* check the PPP path status */
+	if (csid_reg->cmn_reg->num_ppp) {
+		path_status = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_status_addr);
+		CAM_DBG(CAM_ISP, "CSID:%d PPP path status:%d",
+			csid_hw->hw_intf->hw_idx, path_status);
+		/* if status is 0 then it is active */
+		if (!path_status)
+			goto end;
+	}
+
 	/* Check the RDI path status */
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 		path_status = cam_io_r_mb(soc_info->reg_map[0].mem_base +
@@ -461,6 +472,10 @@ static int cam_tfe_csid_global_reset(struct cam_tfe_csid_hw *csid_hw)
 		cam_io_w_mb(0, soc_info->reg_map[0].mem_base +
 			csid_reg->ipp_reg->csid_pxl_irq_mask_addr);
 
+	if (csid_reg->cmn_reg->num_ppp)
+		cam_io_w_mb(0, soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_irq_mask_addr);
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++)
 		cam_io_w_mb(0, soc_info->reg_map[0].mem_base +
 			csid_reg->rdi_reg[i]->csid_rdi_irq_mask_addr);
@@ -478,6 +493,11 @@ static int cam_tfe_csid_global_reset(struct cam_tfe_csid_hw *csid_hw)
 			soc_info->reg_map[0].mem_base +
 			csid_reg->ipp_reg->csid_pxl_irq_clear_addr);
 
+	if (csid_reg->cmn_reg->num_ppp)
+		cam_io_w_mb(csid_reg->cmn_reg->ppp_irq_mask_all,
+			soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_irq_clear_addr);
+
 	for (i = 0 ; i < csid_reg->cmn_reg->num_rdis; i++)
 		cam_io_w_mb(csid_reg->cmn_reg->rdi_irq_mask_all,
 			soc_info->reg_map[0].mem_base +
@@ -541,6 +561,12 @@ static int cam_tfe_csid_global_reset(struct cam_tfe_csid_hw *csid_hw)
 		path_data->res_sof_cnt = 0;
 	}
 
+	if (csid_reg->cmn_reg->num_ppp) {
+		path_data = (struct cam_tfe_csid_path_cfg *)
+			csid_hw->ppp_res.res_priv;
+		path_data->res_sof_cnt = 0;
+	}
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 		path_data = (struct cam_tfe_csid_path_cfg  *)
 			csid_hw->rdi_res[i].res_priv;
@@ -599,6 +625,24 @@ static int cam_tfe_csid_path_reset(struct cam_tfe_csid_hw *csid_hw,
 		val |= TFE_CSID_PATH_INFO_RST_DONE;
 		cam_io_w_mb(val, soc_info->reg_map[0].mem_base +
 			 csid_reg->ipp_reg->csid_pxl_irq_mask_addr);
+	} else if (res->res_id == CAM_TFE_CSID_PATH_RES_PPP) {
+		if (!csid_reg->ppp_reg) {
+			CAM_ERR(CAM_ISP, "CSID:%d PPP not supported :%d",
+				 csid_hw->hw_intf->hw_idx,
+				res->res_id);
+			return -EINVAL;
+		}
+
+		reset_strb_addr = csid_reg->ppp_reg->csid_pxl_rst_strobes_addr;
+		complete = &csid_hw->csid_ppp_complete;
+		reset_strb_val = csid_reg->cmn_reg->ppp_path_rst_stb_all;
+
+		/* Enable path reset done interrupt */
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_irq_mask_addr);
+		val |= TFE_CSID_PATH_INFO_RST_DONE;
+		cam_io_w_mb(val, soc_info->reg_map[0].mem_base +
+			 csid_reg->ppp_reg->csid_pxl_irq_mask_addr);
 	} else {
 		id = res->res_id;
 		if (!csid_reg->rdi_reg[id]) {
@@ -820,7 +864,7 @@ static int cam_tfe_csid_path_reserve(struct cam_tfe_csid_hw *csid_hw,
 			goto end;
 		}
 
-		if (cam_tfe_csid_is_ipp_format_supported(
+		if (cam_tfe_csid_is_ipp_ppp_format_supported(
 				reserve->in_port->format)) {
 			CAM_ERR(CAM_ISP,
 				"CSID:%d res id:%d un support format %d",
@@ -841,6 +885,43 @@ static int cam_tfe_csid_path_reserve(struct cam_tfe_csid_hw *csid_hw,
 
 		break;
 
+	case CAM_TFE_CSID_PATH_RES_PPP:
+		if (csid_hw->ppp_res.res_state !=
+			CAM_ISP_RESOURCE_STATE_AVAILABLE) {
+			CAM_DBG(CAM_ISP,
+				"CSID:%d PPP resource not available %d",
+				csid_hw->hw_intf->hw_idx,
+				csid_hw->ppp_res.res_state);
+			rc = -EINVAL;
+			goto end;
+		}
+
+		if (cam_tfe_csid_is_ipp_ppp_format_supported(
+				reserve->in_port->format)) {
+			CAM_ERR(CAM_ISP,
+				"CSID:%d res id:%d un support format %d",
+				csid_hw->hw_intf->hw_idx, reserve->res_id,
+				reserve->in_port->format);
+			rc = -EINVAL;
+			goto end;
+		}
+
+		rc = cam_tfe_csid_cid_reserve(csid_hw, reserve, &cid_value);
+		if (rc) {
+			CAM_ERR(CAM_ISP,
+				"CSID:%d res id:%d invalid cid %d",
+			       csid_hw->hw_intf->hw_idx, reserve->res_id, cid_value);
+			goto end;
+		}
+
+		/* assign the PPP resource */
+		res = &csid_hw->ppp_res;
+		CAM_DBG(CAM_ISP,
+			"CSID:%d PPP resource:%d acquired successfully",
+			csid_hw->hw_intf->hw_idx, res->res_id);
+
+		break;
+
 	case CAM_TFE_CSID_PATH_RES_RDI_0:
 	case CAM_TFE_CSID_PATH_RES_RDI_1:
 	case CAM_TFE_CSID_PATH_RES_RDI_2:
@@ -899,6 +980,7 @@ static int cam_tfe_csid_path_reserve(struct cam_tfe_csid_hw *csid_hw,
 
 	path_data->bayer_bin = reserve->in_port->bayer_bin;
 	path_data->qcfa_bin = reserve->in_port->qcfa_bin;
+	path_data->crop_enable = reserve->crop_enable;
 
 	csid_hw->event_cb = reserve->event_cb;
 	csid_hw->event_cb_priv = reserve->event_cb_prv;
@@ -912,10 +994,6 @@ static int cam_tfe_csid_path_reserve(struct cam_tfe_csid_hw *csid_hw,
 		}
 	}
 
-	/* Enable crop only for ipp */
-	if (reserve->res_id == CAM_TFE_CSID_PATH_RES_IPP)
-		path_data->crop_enable = true;
-
 	CAM_DBG(CAM_ISP,
 		"Res id: %d height:%d line_start %d line_end %d crop_en %d",
 		reserve->res_id, reserve->in_port->height,
@@ -1177,6 +1255,11 @@ static int cam_tfe_csid_enable_hw(struct cam_tfe_csid_hw  *csid_hw)
 			soc_info->reg_map[0].mem_base +
 			csid_reg->ipp_reg->csid_pxl_irq_clear_addr);
 
+	if (csid_reg->cmn_reg->num_ppp)
+		cam_io_w_mb(csid_reg->cmn_reg->ipp_irq_mask_all,
+			soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_irq_clear_addr);
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++)
 		cam_io_w_mb(csid_reg->cmn_reg->rdi_irq_mask_all,
 			soc_info->reg_map[0].mem_base +
@@ -1207,6 +1290,12 @@ static int cam_tfe_csid_enable_hw(struct cam_tfe_csid_hw  *csid_hw)
 		path_data->res_sof_cnt = 0;
 	}
 
+	if (csid_reg->cmn_reg->num_ppp) {
+		path_data = (struct cam_tfe_csid_path_cfg  *)
+			csid_hw->ppp_res.res_priv;
+		path_data->res_sof_cnt = 0;
+	}
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 		path_data = (struct cam_tfe_csid_path_cfg *)
 			csid_hw->rdi_res[i].res_priv;
@@ -1294,15 +1383,22 @@ static int cam_tfe_csid_init_config_pxl_path(
 	csid_reg = csid_hw->csid_info->csid_reg;
 	soc_info = &csid_hw->hw_info->soc_info;
 
-	pxl_reg = csid_reg->ipp_reg;
+	if (res->res_id == CAM_TFE_CSID_PATH_RES_IPP)
+		pxl_reg = csid_reg->ipp_reg;
+	else
+		pxl_reg = csid_reg->ppp_reg;
+
 	if (!pxl_reg) {
-		CAM_ERR(CAM_ISP, "CSID:%d IPP :%d is not supported on HW",
-			csid_hw->hw_intf->hw_idx, res->res_id);
+		CAM_ERR(CAM_ISP, "CSID:%d %s :%d is not supported on HW",
+			csid_hw->hw_intf->hw_idx,
+			(res->res_id == CAM_TFE_CSID_PATH_RES_IPP) ? "IPP" : "PPP",
+			res->res_id);
 		return -EINVAL;
 	}
 
-	CAM_DBG(CAM_ISP, "Config IPP Path");
-	rc = cam_tfe_csid_get_format_ipp(path_data->in_format,
+	CAM_DBG(CAM_ISP, "Config %s Path",
+			(res->res_id == CAM_TFE_CSID_PATH_RES_IPP) ? "IPP" : "PPP");
+	rc = cam_tfe_csid_get_format_ipp_ppp(path_data->in_format,
 		&decode_format, &plain_format);
 	if (rc)
 		return rc;
@@ -1481,18 +1577,25 @@ static int cam_tfe_csid_deinit_pxl_path(
 	csid_reg = csid_hw->csid_info->csid_reg;
 	soc_info = &csid_hw->hw_info->soc_info;
 
-	pxl_reg = csid_reg->ipp_reg;
+	if (res->res_id == CAM_TFE_CSID_PATH_RES_IPP)
+		pxl_reg = csid_reg->ipp_reg;
+	else
+		pxl_reg = csid_reg->ppp_reg;
+
 	if (res->res_state != CAM_ISP_RESOURCE_STATE_INIT_HW) {
 		CAM_ERR(CAM_ISP,
-			"CSID:%d IPP Res type %d res_id:%d in wrong state %d",
+			"CSID:%d %s Res type %d res_id:%d in wrong state %d",
 			csid_hw->hw_intf->hw_idx,
+			(res->res_id == CAM_TFE_CSID_PATH_RES_IPP) ? "IPP" : "PPP",
 			res->res_type, res->res_id, res->res_state);
 		rc = -EINVAL;
 	}
 
 	if (!pxl_reg) {
-		CAM_ERR(CAM_ISP, "CSID:%d IPP %d is not supported on HW",
-			csid_hw->hw_intf->hw_idx, res->res_id);
+		CAM_ERR(CAM_ISP, "CSID:%d %s %d is not supported on HW",
+			csid_hw->hw_intf->hw_idx,
+			(res->res_id == CAM_TFE_CSID_PATH_RES_IPP) ? "IPP" : "PPP",
+			res->res_id);
 		rc = -EINVAL;
 		goto end;
 	}
@@ -1666,6 +1769,7 @@ static int cam_tfe_csid_disable_pxl_path(
 	}
 
 	pxl_reg = csid_reg->ipp_reg;
+
 	if (res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING) {
 		CAM_DBG(CAM_ISP, "CSID:%d IPP path Res:%d Invalid state%d",
 			csid_hw->hw_intf->hw_idx, res->res_id, res->res_state);
@@ -1718,6 +1822,164 @@ static int cam_tfe_csid_disable_pxl_path(
 	return rc;
 }
 
+static int cam_tfe_csid_enable_ppp_path(
+	struct cam_tfe_csid_hw          *csid_hw,
+	struct cam_isp_resource_node    *res)
+{
+	const struct cam_tfe_csid_reg_offset     *csid_reg;
+	struct cam_hw_soc_info                   *soc_info;
+	struct cam_tfe_csid_path_cfg             *path_data;
+	const struct cam_tfe_csid_pxl_reg_offset *ppp_reg = NULL;
+	uint32_t                                  val = 0;
+
+	path_data = (struct cam_tfe_csid_path_cfg   *) res->res_priv;
+	csid_reg = csid_hw->csid_info->csid_reg;
+	soc_info = &csid_hw->hw_info->soc_info;
+	ppp_reg = csid_reg->ppp_reg;
+
+	if (res->res_state != CAM_ISP_RESOURCE_STATE_INIT_HW) {
+		CAM_ERR(CAM_ISP,
+			"CSID:%d PPP path res type:%d res_id:%d Invalid state%d",
+			csid_hw->hw_intf->hw_idx,
+			res->res_type, res->res_id, res->res_state);
+		return -EINVAL;
+	}
+
+	if (!ppp_reg) {
+		CAM_ERR(CAM_ISP, "CSID:%d PPP resid: %d not supported on HW",
+			csid_hw->hw_intf->hw_idx, res->res_id);
+		return -EINVAL;
+	}
+
+	CAM_DBG(CAM_ISP, "CSID:%d Enable PPP path", csid_hw->hw_intf->hw_idx);
+
+	/* Set master or slave path */
+	if (path_data->sync_mode == CAM_ISP_HW_SYNC_MASTER)
+		/* Set halt mode as master */
+		val = (TFE_CSID_HALT_MODE_SLAVE  << ppp_reg->halt_mode_shift) |
+			(ppp_reg->halt_master_sel_master_val <<
+			ppp_reg->halt_master_sel_shift);
+	else if (path_data->sync_mode == CAM_ISP_HW_SYNC_SLAVE)
+		/* Set halt mode as slave and set master idx */
+		val = (TFE_CSID_HALT_MODE_SLAVE  << ppp_reg->halt_mode_shift) |
+			(ppp_reg->halt_master_sel_slave_val <<
+			ppp_reg->halt_master_sel_shift);
+	else
+		/* Default is internal halt mode */
+		val = 0;
+
+	cam_io_w_mb(val, soc_info->reg_map[0].mem_base + ppp_reg->csid_pxl_ctrl_addr);
+
+	CAM_DBG(CAM_ISP, "CSID:%d PPP Ctrl val: 0x%x", csid_hw->hw_intf->hw_idx, val);
+
+	/* Enable the required ppp path interrupts */
+	val = TFE_CSID_PATH_INFO_RST_DONE | TFE_CSID_PATH_ERROR_FIFO_OVERFLOW |
+		TFE_CSID_PATH_PPP_ERROR_CCIF_VIOLATION | TFE_CSID_PATH_PPP_OVERFLOW_IRQ;
+
+	if (csid_reg->cmn_reg->format_measure_support)
+		val |= TFE_CSID_PATH_ERROR_PIX_COUNT | TFE_CSID_PATH_ERROR_LINE_COUNT;
+
+	if (csid_hw->csid_debug & TFE_CSID_DEBUG_ENABLE_SOF_IRQ)
+		val |= TFE_CSID_PATH_INFO_INPUT_SOF;
+	if (csid_hw->csid_debug & TFE_CSID_DEBUG_ENABLE_EOF_IRQ)
+		val |= TFE_CSID_PATH_INFO_INPUT_EOF;
+
+	cam_io_w_mb(val, soc_info->reg_map[0].mem_base + ppp_reg->csid_pxl_irq_mask_addr);
+
+	CAM_DBG(CAM_ISP, "CSID:%d Enable PPP IRQ mask 0x%x", csid_hw->hw_intf->hw_idx, val);
+
+	res->res_state = CAM_ISP_RESOURCE_STATE_STREAMING;
+
+	return 0;
+}
+
+static int cam_tfe_csid_disable_ppp_path(
+	struct cam_tfe_csid_hw          *csid_hw,
+	struct cam_isp_resource_node    *res,
+	enum cam_tfe_csid_halt_cmd       stop_cmd)
+{
+	int rc = 0;
+	uint32_t val = 0;
+	const struct cam_tfe_csid_reg_offset       *csid_reg;
+	struct cam_hw_soc_info                     *soc_info;
+	struct cam_tfe_csid_path_cfg               *path_data;
+	const struct cam_tfe_csid_pxl_reg_offset   *ppp_reg;
+
+	path_data = (struct cam_tfe_csid_path_cfg   *) res->res_priv;
+	csid_reg = csid_hw->csid_info->csid_reg;
+	soc_info = &csid_hw->hw_info->soc_info;
+
+	if (res->res_id >= CAM_TFE_CSID_PATH_RES_MAX) {
+		CAM_DBG(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",
+			csid_hw->hw_intf->hw_idx, res->res_id, res->res_state);
+		return rc;
+	}
+
+	ppp_reg = csid_reg->ppp_reg;
+	if (res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING) {
+		CAM_DBG(CAM_ISP, "CSID:%d IPP path Res:%d Invalid state%d",
+			csid_hw->hw_intf->hw_idx, res->res_id, res->res_state);
+		return -EINVAL;
+	}
+
+	if (!ppp_reg) {
+		CAM_ERR(CAM_ISP, "CSID:%d PPP %d is not supported on HW",
+			csid_hw->hw_intf->hw_idx, res->res_id);
+		return -EINVAL;
+	}
+
+	if (stop_cmd != CAM_TFE_CSID_HALT_AT_FRAME_BOUNDARY &&
+		stop_cmd != CAM_TFE_CSID_HALT_IMMEDIATELY) {
+		CAM_ERR(CAM_ISP,
+			"CSID:%d PPP path un supported stop command:%d",
+			csid_hw->hw_intf->hw_idx, stop_cmd);
+		return -EINVAL;
+	}
+
+	CAM_DBG(CAM_ISP, "CSID:%d res_id:%d PPP path",
+		csid_hw->hw_intf->hw_idx, res->res_id);
+
+	cam_io_w_mb(0, soc_info->reg_map[0].mem_base +
+		ppp_reg->csid_pxl_irq_mask_addr);
+
+	if (path_data->sync_mode == CAM_ISP_HW_SYNC_MASTER ||
+		path_data->sync_mode == CAM_ISP_HW_SYNC_NONE) {
+		/* configure Halt */
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+		ppp_reg->csid_pxl_ctrl_addr);
+		val &= ~0x3F;
+		val |= (TFE_CSID_HALT_MODE_SLAVE << ppp_reg->halt_mode_shift);
+		val |= (ppp_reg->halt_master_sel_master_val <<
+			ppp_reg->halt_master_sel_shift);
+		val |= stop_cmd;
+		cam_io_w_mb(val, soc_info->reg_map[0].mem_base +
+			ppp_reg->csid_pxl_ctrl_addr);
+	}
+
+	if (path_data->sync_mode == CAM_ISP_HW_SYNC_SLAVE &&
+		stop_cmd == CAM_TFE_CSID_HALT_IMMEDIATELY) {
+		/* configure Halt for slave */
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			ppp_reg->csid_pxl_ctrl_addr);
+		val &= ~0x3F;
+		val |= (TFE_CSID_HALT_MODE_SLAVE << ppp_reg->halt_mode_shift);
+		val |= (ppp_reg->halt_master_sel_slave_val <<
+			ppp_reg->halt_master_sel_shift);
+		val |= stop_cmd;
+		cam_io_w_mb(val, soc_info->reg_map[0].mem_base +
+			ppp_reg->csid_pxl_ctrl_addr);
+	}
+
+	return rc;
+}
+
 static int cam_tfe_csid_init_config_rdi_path(
 	struct cam_tfe_csid_hw          *csid_hw,
 	struct cam_isp_resource_node    *res)
@@ -2032,6 +2294,14 @@ static int cam_tfe_csid_poll_stop_status(
 				CAM_ISP_RESOURCE_STATE_STREAMING)
 				continue;
 
+		} else if (res_id == CAM_TFE_CSID_PATH_RES_PPP) {
+			csid_status_addr =
+			csid_reg->ppp_reg->csid_pxl_status_addr;
+
+			if (csid_hw->ppp_res.res_state !=
+				CAM_ISP_RESOURCE_STATE_STREAMING)
+				continue;
+
 		} else {
 			csid_status_addr =
 				csid_reg->rdi_reg[res_id]->csid_rdi_status_addr;
@@ -2129,6 +2399,19 @@ static int cam_tfe_csid_get_time_stamp(
 				csid_reg->ipp_reg->csid_pxl_timestamp_perv0_sof_addr,
 				&time_stamp->prev_time_stamp_val);
 		}
+	} else if (res->res_id == CAM_TFE_CSID_PATH_RES_PPP) {
+		torn = __cam_tfe_csid_read_timestamp(
+			soc_info->reg_map[0].mem_base,
+			csid_reg->ppp_reg->csid_pxl_timestamp_curr1_sof_addr,
+			csid_reg->ppp_reg->csid_pxl_timestamp_curr0_sof_addr,
+			&time_stamp->time_stamp_val);
+		if (time_stamp->get_prev_timestamp) {
+			prev_torn = __cam_tfe_csid_read_timestamp(
+				soc_info->reg_map[0].mem_base,
+				csid_reg->ppp_reg->csid_pxl_timestamp_perv1_sof_addr,
+				csid_reg->ppp_reg->csid_pxl_timestamp_perv0_sof_addr,
+				&time_stamp->prev_time_stamp_val);
+		}
 	} else {
 		id = res->res_id;
 		rdi_reg = csid_reg->rdi_reg[id];
@@ -2229,6 +2512,11 @@ static int cam_tfe_csid_print_hbi_vbi(
 			csid_reg->ipp_reg->csid_pxl_format_measure1_addr);
 		vbi = cam_io_r_mb(soc_info->reg_map[0].mem_base +
 			csid_reg->ipp_reg->csid_pxl_format_measure2_addr);
+	} else if (res->res_id == CAM_TFE_CSID_PATH_RES_PPP) {
+		hbi = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_format_measure1_addr);
+		vbi = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_format_measure2_addr);
 	} else if ((res->res_id >= CAM_TFE_CSID_PATH_RES_RDI_0) &&
 		(res->res_id <= CAM_TFE_CSID_PATH_RES_RDI_2)) {
 		rdi_reg = csid_reg->rdi_reg[res->res_id];
@@ -2271,6 +2559,7 @@ static int cam_tfe_csid_get_hw_caps(void *hw_priv,
 	struct cam_tfe_csid_hw                *csid_hw;
 	struct cam_hw_info                    *csid_hw_info;
 	const struct cam_tfe_csid_reg_offset  *csid_reg;
+	struct cam_tfe_csid_soc_private       *soc_private;
 
 	if (!hw_priv || !get_hw_cap_args) {
 		CAM_ERR(CAM_ISP, "CSID: Invalid args");
@@ -2281,13 +2570,16 @@ static int cam_tfe_csid_get_hw_caps(void *hw_priv,
 	csid_hw = (struct cam_tfe_csid_hw   *)csid_hw_info->core_info;
 	csid_reg = csid_hw->csid_info->csid_reg;
 	hw_caps = (struct cam_tfe_csid_hw_caps *) get_hw_cap_args;
+	soc_private = (struct cam_tfe_csid_soc_private *) csid_hw_info->soc_info.soc_private;
 
 	hw_caps->num_rdis = csid_reg->cmn_reg->num_rdis;
 	hw_caps->num_pix = csid_hw->pxl_pipe_enable;
+	hw_caps->num_ppp = csid_reg->cmn_reg->num_ppp;
 	hw_caps->major_version = csid_reg->cmn_reg->major_version;
 	hw_caps->minor_version = csid_reg->cmn_reg->minor_version;
 	hw_caps->version_incr = csid_reg->cmn_reg->version_incr;
 	hw_caps->sync_clk = csid_reg->cmn_reg->sync_clk;
+	hw_caps->is_lite = soc_private->is_tfe_csid_lite;
 
 	CAM_DBG(CAM_ISP,
 		"CSID:%d No rdis:%d, no pix:%d, major:%d minor:%d ver :%d",
@@ -2548,7 +2840,8 @@ static int cam_tfe_csid_init_hw(void *hw_priv,
 	if (rc)
 		goto end;
 
-	if (res->res_id == CAM_TFE_CSID_PATH_RES_IPP)
+	if ((res->res_id == CAM_TFE_CSID_PATH_RES_IPP) ||
+		(res->res_id == CAM_TFE_CSID_PATH_RES_PPP))
 		rc = cam_tfe_csid_init_config_pxl_path(csid_hw, res);
 	else
 		rc = cam_tfe_csid_init_config_rdi_path(csid_hw, res);
@@ -2604,7 +2897,8 @@ static int cam_tfe_csid_deinit_hw(void *hw_priv,
 
 	CAM_DBG(CAM_ISP, "De-Init IPP Path: %d", res->res_id);
 
-	if (res->res_id == CAM_TFE_CSID_PATH_RES_IPP)
+	if ((res->res_id == CAM_TFE_CSID_PATH_RES_IPP) ||
+		(res->res_id == CAM_TFE_CSID_PATH_RES_PPP))
 		rc = cam_tfe_csid_deinit_pxl_path(csid_hw, res);
 	else
 		rc = cam_tfe_csid_deinit_rdi_path(csid_hw, res);
@@ -2659,6 +2953,8 @@ static int cam_tfe_csid_start(void *hw_priv, void *start_args,
 	case CAM_ISP_RESOURCE_PIX_PATH:
 		if (res->res_id == CAM_TFE_CSID_PATH_RES_IPP)
 			rc = cam_tfe_csid_enable_pxl_path(csid_hw, res);
+		else if (res->res_id == CAM_TFE_CSID_PATH_RES_PPP)
+			rc = cam_tfe_csid_enable_ppp_path(csid_hw, res);
 		else
 			rc = cam_tfe_csid_enable_rdi_path(csid_hw, res);
 		break;
@@ -2753,6 +3049,9 @@ static int cam_tfe_csid_stop(void *hw_priv,
 			if (res->res_id == CAM_TFE_CSID_PATH_RES_IPP)
 				rc = cam_tfe_csid_disable_pxl_path(csid_hw,
 					res, csid_stop->stop_cmd);
+			else if (res->res_id == CAM_TFE_CSID_PATH_RES_PPP)
+				rc = cam_tfe_csid_disable_ppp_path(csid_hw,
+					res, csid_stop->stop_cmd);
 			else
 				rc = cam_tfe_csid_disable_rdi_path(csid_hw,
 					res, csid_stop->stop_cmd);
@@ -2832,6 +3131,22 @@ static int cam_tfe_csid_sof_irq_debug(
 		}
 	}
 
+	if (csid_reg->ppp_reg) {
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_irq_mask_addr);
+
+		if (val) {
+			if (sof_irq_enable)
+				val |= TFE_CSID_PATH_INFO_INPUT_SOF;
+			else
+				val &= ~TFE_CSID_PATH_INFO_INPUT_SOF;
+
+			cam_io_w_mb(val, soc_info->reg_map[0].mem_base +
+				csid_reg->ppp_reg->csid_pxl_irq_mask_addr);
+			val = 0;
+		}
+	}
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
 			csid_reg->rdi_reg[i]->csid_rdi_irq_mask_addr);
@@ -2981,6 +3296,29 @@ static int cam_tfe_csid_get_regdump(struct cam_tfe_csid_hw *csid_hw,
 			csid_reg->ipp_reg->csid_pxl_vcrop_addr);
 		CAM_INFO(CAM_ISP, "offset 0x%x=0x08%x",
 			csid_reg->ipp_reg->csid_pxl_vcrop_addr, val);
+	} else if (res->res_id == CAM_TFE_CSID_PATH_RES_PPP) {
+		CAM_INFO(CAM_ISP, "Dumping CSID:%d PPP registers ",
+			csid_hw->hw_intf->hw_idx);
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_cfg0_addr);
+		CAM_INFO(CAM_ISP, "offset 0x%x=0x08%x",
+			csid_reg->ppp_reg->csid_pxl_cfg0_addr, val);
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_cfg1_addr);
+		CAM_INFO(CAM_ISP, "offset 0x%x=0x08%x",
+			csid_reg->ppp_reg->csid_pxl_cfg1_addr, val);
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_ctrl_addr);
+		CAM_INFO(CAM_ISP, "offset 0x%x=0x08%x",
+			csid_reg->ppp_reg->csid_pxl_ctrl_addr, val);
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_hcrop_addr);
+		CAM_INFO(CAM_ISP, "offset 0x%x=0x08%x",
+			csid_reg->ppp_reg->csid_pxl_hcrop_addr, val);
+		val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_vcrop_addr);
+		CAM_INFO(CAM_ISP, "offset 0x%x=0x08%x",
+			csid_reg->ppp_reg->csid_pxl_vcrop_addr, val);
 	} else {
 		id = res->res_id;
 		CAM_INFO(CAM_ISP, "Dumping CSID:%d RDI:%d registers ",
@@ -3318,6 +3656,13 @@ static int cam_tfe_csid_evt_bottom_half_handler(
 				csid_hw->hw_intf->hw_idx);
 		}
 
+		if (evt_payload->irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_INFO_INPUT_SOF) {
+			CAM_INFO_RATE_LIMIT(CAM_ISP,
+				"CSID:%d PPP SOF received",
+				csid_hw->hw_intf->hw_idx);
+		}
+
 		for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 			if (evt_payload->irq_status[i] &
 				TFE_CSID_PATH_INFO_INPUT_SOF)
@@ -3327,13 +3672,14 @@ static int cam_tfe_csid_evt_bottom_half_handler(
 		}
 	} else {
 		CAM_ERR_RATE_LIMIT(CAM_ISP,
-			"CSID %d err %d phy %d irq status TOP: 0x%x RX: 0x%x IPP: 0x%x RDI0: 0x%x RDI1: 0x%x RDI2: 0x%x",
+			"CSID %d err %d phy %d irq status TOP: 0x%x RX: 0x%x IPP: 0x%x PPP: 0x%x RDI0: 0x%x RDI1: 0x%x RDI2: 0x%x",
 			csid_hw->hw_intf->hw_idx,
 			evt_payload->evt_type,
 			csid_hw->csi2_rx_cfg.phy_sel,
 			evt_payload->irq_status[TFE_CSID_IRQ_REG_TOP],
 			evt_payload->irq_status[TFE_CSID_IRQ_REG_RX],
 			evt_payload->irq_status[TFE_CSID_IRQ_REG_IPP],
+			evt_payload->irq_status[TFE_CSID_IRQ_REG_PPP],
 			evt_payload->irq_status[TFE_CSID_IRQ_REG_RDI0],
 			evt_payload->irq_status[TFE_CSID_IRQ_REG_RDI1],
 			evt_payload->irq_status[TFE_CSID_IRQ_REG_RDI2]);
@@ -3418,10 +3764,11 @@ irqreturn_t cam_tfe_csid_irq(int irq_num, void *data)
 	struct cam_hw_soc_info                         *soc_info;
 	const struct cam_tfe_csid_reg_offset           *csid_reg;
 	const struct cam_tfe_csid_pxl_reg_offset       *ipp_reg;
+	const struct cam_tfe_csid_pxl_reg_offset       *ppp_reg;
 	const struct cam_tfe_csid_rdi_reg_offset       *rdi_reg;
 	const struct cam_tfe_csid_common_reg_offset    *cmn_reg;
 	const struct cam_tfe_csid_csi2_rx_reg_offset   *csi2_reg;
-	uint32_t                   irq_status[TFE_CSID_IRQ_REG_MAX];
+	uint32_t                   irq_status[TFE_CSID_IRQ_REG_MAX] = {0};
 	bool fatal_err_detected = false, is_error_irq = false;
 	uint32_t sof_irq_debug_en = 0, log_en = 0;
 	unsigned long flags;
@@ -3455,6 +3802,11 @@ irqreturn_t cam_tfe_csid_irq(int irq_num, void *data)
 			cam_io_r_mb(soc_info->reg_map[0].mem_base +
 				csid_reg->ipp_reg->csid_pxl_irq_status_addr);
 
+	if (csid_reg->cmn_reg->num_ppp)
+		irq_status[TFE_CSID_IRQ_REG_PPP] =
+			cam_io_r_mb(soc_info->reg_map[0].mem_base +
+				csid_reg->ppp_reg->csid_pxl_irq_status_addr);
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++)
 		irq_status[i] =
 		cam_io_r_mb(soc_info->reg_map[0].mem_base +
@@ -3474,6 +3826,11 @@ irqreturn_t cam_tfe_csid_irq(int irq_num, void *data)
 			soc_info->reg_map[0].mem_base +
 			csid_reg->ipp_reg->csid_pxl_irq_clear_addr);
 
+	if (csid_reg->cmn_reg->num_ppp)
+		cam_io_w_mb(irq_status[TFE_CSID_IRQ_REG_PPP],
+			soc_info->reg_map[0].mem_base +
+			csid_reg->ppp_reg->csid_pxl_irq_clear_addr);
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 		cam_io_w_mb(irq_status[i],
 			soc_info->reg_map[0].mem_base +
@@ -3697,6 +4054,11 @@ handle_fatal_error:
 			CAM_INFO_RATE_LIMIT(CAM_ISP,
 				"CSID IPP reset complete");
 
+		if (irq_status[TFE_CSID_IRQ_REG_PPP] &
+			BIT(csid_reg->cmn_reg->path_rst_done_shift_val))
+			CAM_INFO_RATE_LIMIT(CAM_ISP,
+				"CSID PPP reset complete");
+
 		if (irq_status[TFE_CSID_IRQ_REG_TOP])
 			CAM_INFO_RATE_LIMIT(CAM_ISP,
 				"CSID TOP reset complete");
@@ -3778,6 +4140,77 @@ handle_fatal_error:
 
 	}
 
+	/* read the PPP errors */
+	if (csid_reg->cmn_reg->num_ppp) {
+		/* PPP reset done bit */
+		if (irq_status[TFE_CSID_IRQ_REG_PPP] &
+			BIT(csid_reg->cmn_reg->path_rst_done_shift_val)) {
+			CAM_DBG(CAM_ISP, "CSID PPP reset complete");
+			complete(&csid_hw->csid_ppp_complete);
+		}
+
+		if ((irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_INFO_INPUT_SOF) &&
+			(csid_hw->csid_debug & TFE_CSID_DEBUG_ENABLE_SOF_IRQ)) {
+			if (!csid_hw->sof_irq_triggered)
+				CAM_INFO_RATE_LIMIT(CAM_ISP,
+				"CSID:%d PPP SOF received",
+					csid_hw->hw_intf->hw_idx);
+			else
+				log_en = 1;
+
+			if (csid_hw->sof_irq_triggered)
+				csid_hw->irq_debug_cnt++;
+		}
+
+		if ((irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_INFO_INPUT_EOF) &&
+			(csid_hw->csid_debug & TFE_CSID_DEBUG_ENABLE_EOF_IRQ)) {
+			CAM_INFO_RATE_LIMIT(CAM_ISP, "CSID:%d PPP EOF received",
+				csid_hw->hw_intf->hw_idx);
+		}
+
+		if (irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_ERROR_FIFO_OVERFLOW) {
+			/* Stop PPP path immediately */
+			cam_io_w_mb(CAM_TFE_CSID_HALT_IMMEDIATELY,
+				soc_info->reg_map[0].mem_base +
+				csid_reg->ppp_reg->csid_pxl_ctrl_addr);
+			is_error_irq = true;
+		}
+
+		if (irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_PPP_ERROR_CCIF_VIOLATION)
+			is_error_irq = true;
+
+		if ((irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_ERROR_PIX_COUNT) ||
+			(irq_status[TFE_CSID_IRQ_REG_PPP] &
+			TFE_CSID_PATH_ERROR_LINE_COUNT)) {
+			ppp_reg = csid_reg->ppp_reg;
+			cmn_reg = csid_reg->cmn_reg;
+			val = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+				ppp_reg->csid_pxl_format_measure0_addr);
+			val1 = cam_io_r_mb(soc_info->reg_map[0].mem_base +
+				ppp_reg->csid_pxl_format_measure_cfg1_addr);
+
+			CAM_ERR(CAM_ISP,
+				"Pix/Line count error for CSID: %d PPP path, Expected:: height: %d, width: %d and  Actual:: height: %d width %d",
+				csid_hw->hw_intf->hw_idx,
+				((val1 >>
+				cmn_reg->format_measure_height_shift_val) &
+				cmn_reg->format_measure_height_mask_val),
+				val1 &
+				cmn_reg->format_measure_width_mask_val,
+				((val >>
+				cmn_reg->format_measure_height_shift_val) &
+				cmn_reg->format_measure_height_mask_val),
+				val &
+				cmn_reg->format_measure_width_mask_val);
+		}
+
+	}
+
 	for (i = 0; i < csid_reg->cmn_reg->num_rdis; i++) {
 
 		if ((irq_status[i] &
@@ -3857,13 +4290,14 @@ handle_fatal_error:
 	}
 
 	if (is_error_irq || log_en) {
-		CAM_ERR_RATE_LIMIT(CAM_ISP,
-			"CSID %d irq status TOP: 0x%x RX: 0x%x IPP: 0x%x",
+		CAM_ERR(CAM_ISP,
+			"CSID %d irq status TOP: 0x%x RX: 0x%x IPP: 0x%x PPP: 0x%x",
 			csid_hw->hw_intf->hw_idx,
 			irq_status[TFE_CSID_IRQ_REG_TOP],
 			irq_status[TFE_CSID_IRQ_REG_RX],
-			irq_status[TFE_CSID_IRQ_REG_IPP]);
-		CAM_ERR_RATE_LIMIT(CAM_ISP,
+			irq_status[TFE_CSID_IRQ_REG_IPP],
+			irq_status[TFE_CSID_IRQ_REG_PPP]);
+		CAM_ERR(CAM_ISP,
 			"RDI0: 0x%x RDI1: 0x%x RDI2: 0x%x CSID clk:%d",
 			irq_status[TFE_CSID_IRQ_REG_RDI0],
 			irq_status[TFE_CSID_IRQ_REG_RDI1],
@@ -3891,6 +4325,7 @@ int cam_tfe_csid_hw_probe_init(struct cam_hw_intf  *csid_hw_intf,
 	struct cam_tfe_csid_path_cfg         *path_data;
 	struct cam_hw_info                   *csid_hw_info;
 	struct cam_tfe_csid_hw               *tfe_csid_hw = NULL;
+	struct cam_tfe_csid_soc_private      *soc_private = NULL;
 	const struct cam_tfe_csid_reg_offset *csid_reg;
 
 	if (csid_idx >= CAM_TFE_CSID_HW_NUM_MAX) {
@@ -3918,6 +4353,7 @@ int cam_tfe_csid_hw_probe_init(struct cam_hw_intf  *csid_hw_intf,
 	init_completion(&tfe_csid_hw->csid_top_complete);
 	init_completion(&tfe_csid_hw->csid_csi2_complete);
 	init_completion(&tfe_csid_hw->csid_ipp_complete);
+	init_completion(&tfe_csid_hw->csid_ppp_complete);
 	for (i = 0; i < CAM_TFE_CSID_RDI_MAX; i++)
 		init_completion(&tfe_csid_hw->csid_rdin_complete[i]);
 
@@ -3940,6 +4376,8 @@ int cam_tfe_csid_hw_probe_init(struct cam_hw_intf  *csid_hw_intf,
 		goto err;
 	}
 
+	soc_private = (struct cam_tfe_csid_soc_private *) csid_hw_info->soc_info.soc_private;
+
 	tfe_csid_hw->hw_intf->hw_ops.get_hw_caps = cam_tfe_csid_get_hw_caps;
 	tfe_csid_hw->hw_intf->hw_ops.init        = cam_tfe_csid_init_hw;
 	tfe_csid_hw->hw_intf->hw_ops.deinit      = cam_tfe_csid_deinit_hw;
@@ -3986,7 +4424,7 @@ int cam_tfe_csid_hw_probe_init(struct cam_hw_intf  *csid_hw_intf,
 		csid_reg->cmn_reg->top_tfe2_pix_pipe_fuse_reg);
 
 	/* Initialize the IPP resources */
-	if (!(val && (tfe_csid_hw->hw_intf->hw_idx == 2))) {
+	if (!soc_private->is_tfe_csid_lite && !(val && (tfe_csid_hw->hw_intf->hw_idx == 2))) {
 		CAM_DBG(CAM_ISP, "initializing the pix path");
 
 		tfe_csid_hw->ipp_res.res_type = CAM_ISP_RESOURCE_PIX_PATH;
@@ -4004,6 +4442,24 @@ int cam_tfe_csid_hw_probe_init(struct cam_hw_intf  *csid_hw_intf,
 		tfe_csid_hw->pxl_pipe_enable = 1;
 	}
 
+	/* Initialize the PPP resources */
+	if (tfe_csid_hw->csid_info->csid_reg->cmn_reg->num_ppp) {
+		CAM_DBG(CAM_ISP, "initializing the ppp path");
+
+		tfe_csid_hw->ppp_res.res_type = CAM_ISP_RESOURCE_PIX_PATH;
+		tfe_csid_hw->ppp_res.res_id = CAM_TFE_CSID_PATH_RES_PPP;
+		tfe_csid_hw->ppp_res.res_state =
+			CAM_ISP_RESOURCE_STATE_AVAILABLE;
+		tfe_csid_hw->ppp_res.hw_intf = tfe_csid_hw->hw_intf;
+		path_data = kzalloc(sizeof(*path_data),
+					GFP_KERNEL);
+		if (!path_data) {
+			rc = -ENOMEM;
+			goto err;
+		}
+		tfe_csid_hw->ppp_res.res_priv = path_data;
+	}
+
 	/* Initialize the RDI resource */
 	for (i = 0; i < tfe_csid_hw->csid_info->csid_reg->cmn_reg->num_rdis;
 			i++) {
@@ -4071,6 +4527,8 @@ int cam_tfe_csid_hw_probe_init(struct cam_hw_intf  *csid_hw_intf,
 err:
 	if (rc) {
 		kfree(tfe_csid_hw->ipp_res.res_priv);
+		if (tfe_csid_hw->csid_info->csid_reg->cmn_reg->num_ppp)
+			kfree(tfe_csid_hw->ppp_res.res_priv);
 		for (i = 0; i <
 			tfe_csid_hw->csid_info->csid_reg->cmn_reg->num_rdis;
 			i++)
@@ -4094,6 +4552,9 @@ int cam_tfe_csid_hw_deinit(struct cam_tfe_csid_hw *tfe_csid_hw)
 	/* release the privdate data memory from resources */
 	kfree(tfe_csid_hw->ipp_res.res_priv);
 
+	if (tfe_csid_hw->csid_info->csid_reg->cmn_reg->num_ppp)
+		kfree(tfe_csid_hw->ppp_res.res_priv);
+
 	for (i = 0; i <
 		tfe_csid_hw->csid_info->csid_reg->cmn_reg->num_rdis;
 		i++) {

+ 43 - 14
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_core.h

@@ -56,11 +56,14 @@
 #define TFE_CSID_PATH_ERROR_PIX_COUNT                 BIT(13)
 #define TFE_CSID_PATH_ERROR_LINE_COUNT                BIT(14)
 #define TFE_CSID_PATH_IPP_ERROR_CCIF_VIOLATION        BIT(15)
-#define TFE_CSID_PATH_IPP_OVERFLOW_IRQ                BIT(16)
-#define TFE_CSID_PATH_IPP_FRAME_DROP                  BIT(17)
+#define TFE_CSID_PATH_IPP_FRAME_DROP                  BIT(16)
+#define TFE_CSID_PATH_IPP_OVERFLOW_IRQ                BIT(17)
+#define TFE_CSID_PATH_PPP_ERROR_CCIF_VIOLATION        BIT(15)
+#define TFE_CSID_PATH_PPP_FRAME_DROP                  BIT(16)
+#define TFE_CSID_PATH_PPP_OVERFLOW_IRQ                BIT(17)
+#define TFE_CSID_PATH_RDI_ERROR_CCIF_VIOLATION        BIT(15)
 #define TFE_CSID_PATH_RDI_FRAME_DROP                  BIT(16)
 #define TFE_CSID_PATH_RDI_OVERFLOW_IRQ                BIT(17)
-#define TFE_CSID_PATH_RDI_ERROR_CCIF_VIOLATION        BIT(18)
 
 /*
  * Debug values enable the corresponding interrupts and debug logs provide
@@ -95,6 +98,14 @@ enum cam_tfe_csid_path_halt_mode {
 	TFE_CSID_HALT_MODE_SLAVE,
 };
 
+/* enum cam_csid_path_halt_master select the path halt master control */
+enum cam_tfe_csid_path_halt_master_sel {
+	TFE_CSID_HALT_CMD_SOURCE_EXTERNAL,
+	TFE_CSID_HALT_CMD_SOURCE_NONE,
+	TFE_CSID_HALT_CMD_SOURCE_INTERNAL2,
+	TFE_CSID_HALT_CMD_SOURCE_INTERNAL1,
+};
+
 /**
  *enum cam_csid_path_timestamp_stb_sel - select the sof/eof strobes used to
  *        capture the timestamp
@@ -116,11 +127,20 @@ struct cam_tfe_csid_pxl_reg_offset {
 	uint32_t csid_pxl_cfg0_addr;
 	uint32_t csid_pxl_cfg1_addr;
 	uint32_t csid_pxl_ctrl_addr;
+	uint32_t csid_pxl_frame_drop_pattern;
+	uint32_t csid_pxl_frame_drop_period;
+	uint32_t csid_pxl_irq_subsample_pattern;
+	uint32_t csid_pxl_irq_subsample_period;
 	uint32_t csid_pxl_hcrop_addr;
 	uint32_t csid_pxl_vcrop_addr;
 	uint32_t csid_pxl_rst_strobes_addr;
 	uint32_t csid_pxl_status_addr;
 	uint32_t csid_pxl_misr_val_addr;
+	uint32_t csid_pxl_format_measure_cfg0_addr;
+	uint32_t csid_pxl_format_measure_cfg1_addr;
+	uint32_t csid_pxl_format_measure0_addr;
+	uint32_t csid_pxl_format_measure1_addr;
+	uint32_t csid_pxl_format_measure2_addr;
 	uint32_t csid_pxl_timestamp_curr0_sof_addr;
 	uint32_t csid_pxl_timestamp_curr1_sof_addr;
 	uint32_t csid_pxl_timestamp_perv0_sof_addr;
@@ -129,15 +149,11 @@ struct cam_tfe_csid_pxl_reg_offset {
 	uint32_t csid_pxl_timestamp_curr1_eof_addr;
 	uint32_t csid_pxl_timestamp_perv0_eof_addr;
 	uint32_t csid_pxl_timestamp_perv1_eof_addr;
+	uint32_t csid_pxl_ppp_sparse_pd_ext_cfg0;
 	uint32_t csid_pxl_err_recovery_cfg0_addr;
 	uint32_t csid_pxl_err_recovery_cfg1_addr;
 	uint32_t csid_pxl_err_recovery_cfg2_addr;
 	uint32_t csid_pxl_multi_vcdt_cfg0_addr;
-	uint32_t csid_pxl_format_measure_cfg0_addr;
-	uint32_t csid_pxl_format_measure_cfg1_addr;
-	uint32_t csid_pxl_format_measure0_addr;
-	uint32_t csid_pxl_format_measure1_addr;
-	uint32_t csid_pxl_format_measure2_addr;
 
 	/* configuration */
 	uint32_t pix_store_en_shift_val;
@@ -164,10 +180,21 @@ struct cam_tfe_csid_rdi_reg_offset {
 	uint32_t csid_rdi_cfg0_addr;
 	uint32_t csid_rdi_cfg1_addr;
 	uint32_t csid_rdi_ctrl_addr;
+	uint32_t csid_rdi_frame_drop_pattern;
+	uint32_t csid_rdi_frame_drop_period;
+	uint32_t csid_rdi_irq_subsample_pattern;
+	uint32_t csid_rdi_irq_subsample_period;
 	uint32_t csid_rdi_rst_strobes_addr;
 	uint32_t csid_rdi_status_addr;
 	uint32_t csid_rdi_misr_val0_addr;
 	uint32_t csid_rdi_misr_val1_addr;
+	uint32_t csid_rdi_misr_val2_addr;
+	uint32_t csid_rdi_misr_val3_addr;
+	uint32_t csid_rdi_format_measure_cfg0_addr;
+	uint32_t csid_rdi_format_measure_cfg1_addr;
+	uint32_t csid_rdi_format_measure0_addr;
+	uint32_t csid_rdi_format_measure1_addr;
+	uint32_t csid_rdi_format_measure2_addr;
 	uint32_t csid_rdi_timestamp_curr0_sof_addr;
 	uint32_t csid_rdi_timestamp_curr1_sof_addr;
 	uint32_t csid_rdi_timestamp_prev0_sof_addr;
@@ -182,11 +209,6 @@ struct cam_tfe_csid_rdi_reg_offset {
 	uint32_t csid_rdi_byte_cntr_ping_addr;
 	uint32_t csid_rdi_byte_cntr_pong_addr;
 	uint32_t csid_rdi_multi_vcdt_cfg0_addr;
-	uint32_t csid_rdi_format_measure_cfg0_addr;
-	uint32_t csid_rdi_format_measure_cfg1_addr;
-	uint32_t csid_rdi_format_measure0_addr;
-	uint32_t csid_rdi_format_measure1_addr;
-	uint32_t csid_rdi_format_measure2_addr;
 
 	/* configuration */
 	uint32_t packing_format;
@@ -259,10 +281,12 @@ struct cam_tfe_csid_common_reg_offset {
 	uint32_t version_incr;
 	uint32_t num_rdis;
 	uint32_t num_pix;
+	uint32_t num_ppp;
 	uint32_t csid_reg_rst_stb;
 	uint32_t csid_rst_stb;
 	uint32_t csid_rst_stb_sw_all;
 	uint32_t ipp_path_rst_stb_all;
+	uint32_t ppp_path_rst_stb_all;
 	uint32_t rdi_path_rst_stb_all;
 	uint32_t path_rst_done_shift_val;
 	uint32_t path_en_shift_val;
@@ -278,6 +302,7 @@ struct cam_tfe_csid_common_reg_offset {
 	uint32_t crop_h_en_shift_val;
 	uint32_t crop_shift;
 	uint32_t ipp_irq_mask_all;
+	uint32_t ppp_irq_mask_all;
 	uint32_t rdi_irq_mask_all;
 	uint32_t top_tfe2_pix_pipe_fuse_reg;
 	uint32_t top_tfe2_fuse_reg;
@@ -301,6 +326,7 @@ struct cam_tfe_csid_reg_offset {
 	const struct cam_tfe_csid_common_reg_offset   *cmn_reg;
 	const struct cam_tfe_csid_csi2_rx_reg_offset  *csi2_reg;
 	const struct cam_tfe_csid_pxl_reg_offset      *ipp_reg;
+	const struct cam_tfe_csid_pxl_reg_offset      *ppp_reg;
 	const struct cam_tfe_csid_rdi_reg_offset *rdi_reg[CAM_TFE_CSID_RDI_MAX];
 };
 
@@ -453,13 +479,14 @@ struct cam_csid_evt_payload {
  * @in_res_id:                csid in resource type
  * @csi2_rx_cfg:              csi2 rx decoder configuration for csid
  * @csi2_rx_reserve_cnt:      csi2 reservations count value
+ * pxl_pipe_enable:           flag to specify if the hardware has IPP
  * @ipp_res:                  image pixel path resource
+ * @ppp_res:                  PD pixel path resource
  * @rdi_res:                  raw dump image path resources
  * @cid_res:                  cid resources values
  * @csid_top_reset_complete:  csid top reset completion
  * @csid_csi2_reset_complete: csi2 reset completion
  * @csid_ipp_reset_complete:  ipp reset completion
- * @csid_ppp_complete:        ppp reset completion
  * @csid_rdin_reset_complete: rdi n completion
  * @csid_debug:               csid debug information to enable the SOT, EOT,
  *                            SOF, EOF, measure etc in the csid hw
@@ -495,11 +522,13 @@ struct cam_tfe_csid_hw {
 	uint32_t                            csi2_reserve_cnt;
 	uint32_t                            pxl_pipe_enable;
 	struct cam_isp_resource_node        ipp_res;
+	struct cam_isp_resource_node        ppp_res;
 	struct cam_isp_resource_node        rdi_res[CAM_TFE_CSID_RDI_MAX];
 	struct cam_tfe_csid_cid_data        cid_res[CAM_TFE_CSID_CID_MAX];
 	struct completion                   csid_top_complete;
 	struct completion                   csid_csi2_complete;
 	struct completion                   csid_ipp_complete;
+	struct completion                   csid_ppp_complete;
 	struct completion     csid_rdin_complete[CAM_TFE_CSID_RDI_MAX];
 	uint64_t                            csid_debug;
 	uint64_t                            clk_rate;

+ 4 - 1
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_soc.c

@@ -24,7 +24,6 @@ int cam_tfe_csid_init_soc_resources(struct cam_hw_soc_info *soc_info,
 
 	soc_info->soc_private = soc_private;
 
-
 	rc = cam_soc_util_get_dt_properties(soc_info);
 	if (rc < 0)
 		return rc;
@@ -32,6 +31,10 @@ int cam_tfe_csid_init_soc_resources(struct cam_hw_soc_info *soc_info,
 	for (i = 0; i < soc_info->irq_count; i++)
 		irq_data[i] = data;
 
+	soc_private->is_tfe_csid_lite = false;
+	if (strnstr(soc_info->compatible, "lite", strlen(soc_info->compatible)) != NULL)
+		soc_private->is_tfe_csid_lite = true;
+
 	/* Need to see if we want post process the clock list */
 	rc = cam_soc_util_request_platform_resource(soc_info, csid_irq_handler, &(irq_data[0]));
 	if (rc < 0) {

+ 3 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_csid_hw/cam_tfe_csid_soc.h

@@ -1,6 +1,7 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 /*
  * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
  */
 
 #ifndef _CAM_TFE_CSID_SOC_H_
@@ -16,9 +17,11 @@
  * @cpas_handle:             Handle returned on registering with CPAS driver.
  *                           This handle is used for all further interface
  *                           with CPAS.
+ * @is_tfe_csid_lite:        Flag to indicate if it is CSID lite HW
  */
 struct cam_tfe_csid_soc_private {
 	uint32_t cpas_handle;
+	bool     is_tfe_csid_lite;
 };
 
 /**

+ 16 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe.c

@@ -1,11 +1,15 @@
 // SPDX-License-Identifier: GPL-2.0-only
 /*
  * Copyright (c) 2019-2021, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
  */
 
 #include <linux/module.h>
 #include "cam_tfe530.h"
 #include "cam_tfe640.h"
+#include "cam_tfe640_210.h"
+#include "cam_tfe770.h"
+#include "cam_tfe_lite770.h"
 #include "cam_tfe_hw_intf.h"
 #include "cam_tfe_core.h"
 #include "cam_tfe_dev.h"
@@ -20,6 +24,18 @@ static const struct of_device_id cam_tfe_dt_match[] = {
 		.compatible = "qcom,tfe640",
 		.data = &cam_tfe640,
 	},
+	{
+		.compatible = "qcom,tfe640_210",
+		.data = &cam_tfe640_210,
+	},
+	{
+		.compatible = "qcom,tfe770",
+		.data = &cam_tfe770,
+	},
+	{
+		.compatible = "qcom,tfe-lite770",
+		.data = &cam_tfe_lite770,
+	},
 	{}
 };
 MODULE_DEVICE_TABLE(of, cam_tfe_dt_match);

+ 21 - 2
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe530.h

@@ -18,7 +18,7 @@ static struct cam_tfe_top_reg_offset_common  tfe530_top_commong_reg  = {
 	.stats_feature                          = 0x0000100C,
 	.zoom_feature                           = 0x00001010,
 	.global_reset_cmd                       = 0x00001014,
-	.core_cgc_ctrl                          = 0x00001018,
+	.core_cgc_ctrl_0                        = 0x00001018,
 	.ahb_cgc_ctrl                           = 0x0000101C,
 	.core_cfg_0                             = 0x00001024,
 	.core_cfg_1                             = 0x00001028,
@@ -53,6 +53,24 @@ static struct cam_tfe_top_reg_offset_common  tfe530_top_commong_reg  = {
 	.diag_neq_hbi_shift                     = 14,
 	.diag_sensor_hbi_mask                   = 0x3FFF,
 	.serializer_supported                   = false,
+	.pp_camif_violation_bit                 = BIT(0),
+	.pp_violation_bit                       = BIT(1),
+	.rdi0_camif_violation_bit               = BIT(2),
+	.rdi1_camif_violation_bit               = BIT(3),
+	.rdi2_camif_violation_bit               = BIT(4),
+	.diag_violation_bit                     = BIT(5),
+	.pp_frame_drop_bit                      = BIT(8),
+	.rdi0_frame_drop_bit                    = BIT(9),
+	.rdi1_frame_drop_bit                    = BIT(10),
+	.rdi2_frame_drop_bit                    = BIT(11),
+	.pp_overflow_bit                        = BIT(16),
+	.rdi0_overflow_bit                      = BIT(17),
+	.rdi1_overflow_bit                      = BIT(18),
+	.rdi2_overflow_bit                      = BIT(19),
+	.mup_shift_val                          = 0,
+	.mup_supported                          = false,
+	.height_shift                           = 16,
+	.epoch_shift_val                        = 16,
 };
 
 static struct cam_tfe_camif_reg  tfe530_camif_reg = {
@@ -220,7 +238,6 @@ static struct cam_tfe_rdi_reg_data tfe530_rdi2_reg_data = {
 	.enable_diagnostic_hw        = 0x1,
 	.diag_sensor_sel             = 0x3,
 	.diag_sensor_shift           = 0x1,
-
 };
 
 static struct cam_tfe_clc_hw_status  tfe530_clc_hw_info[CAM_TFE_MAX_CLC] = {
@@ -859,6 +876,8 @@ static struct cam_tfe_bus_hw_info  tfe530_bus_hw_info = {
 	.max_bw_counter_limit  = 0xFF,
 	.counter_limit_shift   = 1,
 	.counter_limit_mask    = 0xF,
+	.en_cfg_shift = 16,
+	.height_shift = 16,
 };
 
 struct cam_tfe_hw_info cam_tfe530 = {

+ 21 - 2
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe640.h

@@ -18,7 +18,7 @@ static struct cam_tfe_top_reg_offset_common  tfe640_top_commong_reg  = {
 	.stats_feature                          = 0x0000180C,
 	.zoom_feature                           = 0x00001810,
 	.global_reset_cmd                       = 0x00001814,
-	.core_cgc_ctrl                          = 0x00001818,
+	.core_cgc_ctrl_0                        = 0x00001818,
 	.ahb_cgc_ctrl                           = 0x0000181C,
 	.core_cfg_0                             = 0x00001824,
 	.reg_update_cmd                         = 0x0000182C,
@@ -66,6 +66,24 @@ static struct cam_tfe_top_reg_offset_common  tfe640_top_commong_reg  = {
 	.diag_neq_hbi_shift                     = 14,
 	.diag_sensor_hbi_mask                   = 0x3FFF,
 	.serializer_supported                   = true,
+	.pp_camif_violation_bit                 = BIT(0),
+	.pp_violation_bit                       = BIT(1),
+	.rdi0_camif_violation_bit               = BIT(2),
+	.rdi1_camif_violation_bit               = BIT(3),
+	.rdi2_camif_violation_bit               = BIT(4),
+	.diag_violation_bit                     = BIT(5),
+	.pp_frame_drop_bit                      = BIT(8),
+	.rdi0_frame_drop_bit                    = BIT(9),
+	.rdi1_frame_drop_bit                    = BIT(10),
+	.rdi2_frame_drop_bit                    = BIT(11),
+	.pp_overflow_bit                        = BIT(16),
+	.rdi0_overflow_bit                      = BIT(17),
+	.rdi1_overflow_bit                      = BIT(18),
+	.rdi2_overflow_bit                      = BIT(19),
+	.mup_shift_val                          = 0,
+	.mup_supported                          = false,
+	.height_shift                           = 16,
+	.epoch_shift_val                        = 16,
 };
 
 static struct cam_tfe_camif_reg  tfe640_camif_reg = {
@@ -235,7 +253,6 @@ static struct cam_tfe_rdi_reg_data tfe640_rdi2_reg_data = {
 	.enable_diagnostic_hw        = 0x1,
 	.diag_sensor_sel             = 0x3,
 	.diag_sensor_shift           = 0x1,
-
 };
 
 static struct cam_tfe_clc_hw_status  tfe640_clc_hw_info[CAM_TFE_MAX_CLC] = {
@@ -1175,6 +1192,8 @@ static struct cam_tfe_bus_hw_info  tfe640_bus_hw_info = {
 	.max_bw_counter_limit  = 0xFF,
 	.counter_limit_shift   = 1,
 	.counter_limit_mask    = 0xF,
+	.en_cfg_shift = 16,
+	.height_shift = 16,
 };
 
 struct cam_tfe_hw_info cam_tfe640 = {

+ 1423 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe770.h

@@ -0,0 +1,1423 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+/*
+ * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
+ */
+
+
+#ifndef _CAM_TFE770_H_
+#define _CAM_TFE770_H_
+#include <media/cam_isp_tfe.h>
+#include "cam_tfe_core.h"
+#include "cam_tfe_bus.h"
+
+
+static struct cam_tfe_top_reg_offset_common  tfe770_top_commong_reg  = {
+	.hw_version                             = 0x00001800,
+	.hw_capability                          = 0x00001804,
+	.lens_feature                           = 0x00001808,
+	.stats_feature                          = 0x0000180C,
+	.zoom_feature                           = 0x00001810,
+	.global_reset_cmd                       = 0x00001814,
+	.core_cgc_ctrl_0                        = 0x00001818,
+	.core_cgc_ctrl_1                        = 0x0000181C,
+	.ahb_cgc_ctrl                           = 0x0000181C,
+	.core_cfg_0                             = 0x00001824,
+	.reg_update_cmd                         = 0x0000182C,
+	.diag_config                            = 0x00001860,
+	.diag_sensor_status_0                   = 0x00001864,
+	.diag_sensor_status_1                   = 0x00001868,
+	.diag_sensor_frame_cnt_status           = 0x0000186C,
+	.violation_status                       = 0x00001870,
+	.stats_throttle_cnt_cfg_0               = 0x00001874,
+	.stats_throttle_cnt_cfg_1               = 0x00001878,
+	.num_debug_reg                          = 12,
+	.debug_reg = {
+		0x000018A0,
+		0x000018A4,
+		0x000018A8,
+		0x000018AC,
+		0x000018B0,
+		0x000018B4,
+		0x000018B8,
+		0x000018BC,
+		0x000018C0,
+		0x000018C4,
+		0x000018C8,
+		0x000018CC,
+	},
+	.debug_cfg                              = 0x000018DC,
+	.num_perf_cfg                           = 2,
+	.perf_cfg = {
+		{
+			.perf_cnt_cfg           = 0x000018E0,
+			.perf_pixel_count       = 0x000018E4,
+			.perf_line_count        = 0x000018E8,
+			.perf_stall_count       = 0x000018EC,
+			.perf_always_count      = 0x000018F0,
+			.perf_count_status      = 0x000018F4,
+		},
+		{
+			.perf_cnt_cfg           = 0x000018F8,
+			.perf_pixel_count       = 0x000018FC,
+			.perf_line_count        = 0x00001900,
+			.perf_stall_count       = 0x00001904,
+			.perf_always_count      = 0x00001908,
+			.perf_count_status      = 0x0000190C,
+		},
+	},
+	.diag_sensor_frame_cnt_status_1         = 0x00001920,
+	.diag_min_hbi_error_shift               = 15,
+	.diag_neq_hbi_shift                     = 14,
+	.diag_sensor_hbi_mask                   = 0x3FFF,
+	.serializer_supported                   = true,
+};
+
+static struct cam_tfe_camif_reg  tfe770_camif_reg = {
+	.hw_version                   = 0x00001C00,
+	.hw_status                    = 0x00001C04,
+	.module_cfg                   = 0x00001C60,
+	.pdaf_raw_crop_width_cfg      = 0x00001C68,
+	.pdaf_raw_crop_height_cfg     = 0x00001C6C,
+	.line_skip_pattern            = 0x00001C70,
+	.pixel_skip_pattern           = 0x00001C74,
+	.period_cfg                   = 0x00001C78,
+	.irq_subsample_pattern        = 0x00001C7C,
+	.epoch_irq_cfg                = 0x00001C80,
+	.debug_1                      = 0x00001DF0,
+	.debug_0                      = 0x00001DF4,
+	.test_bus_ctrl                = 0x00001DF8,
+	.spare                        = 0x00001DFC,
+	.reg_update_cmd               = 0x0000182C,
+};
+
+static struct cam_tfe_camif_reg_data tfe770_camif_reg_data = {
+	.extern_reg_update_mask       = 0x00000001,
+	.dual_tfe_pix_en_shift        = 0x00000001,
+	.extern_reg_update_shift      = 0x0,
+	.dual_tfe_sync_sel_shift      = 18,
+	.delay_line_en_shift          = 8,
+	.pixel_pattern_shift          = 24,
+	.pixel_pattern_mask           = 0x7000000,
+	.module_enable_shift          = 0,
+	.pix_out_enable_shift         = 8,
+	.pdaf_output_enable_shift     = 9,
+	.dsp_mode_shift               = 0,
+	.dsp_mode_mask                = 0,
+	.dsp_en_shift                 = 0,
+	.dsp_en_mask                  = 0,
+	.reg_update_cmd_data          = 0x1,
+	.epoch_line_cfg               = 0x00140014,
+	.sof_irq_mask                 = 0x00000001,
+	.epoch0_irq_mask              = 0x00000004,
+	.epoch1_irq_mask              = 0x00000008,
+	.eof_irq_mask                 = 0x00000002,
+	.reg_update_irq_mask          = 0x00000001,
+	.error_irq_mask0              = 0x00010100,
+	.error_irq_mask2              = 0x00000023,
+	.subscribe_irq_mask           = {
+		0x00000000,
+		0x00000007,
+		0x00000000,
+	},
+	.enable_diagnostic_hw         = 0x1,
+	.perf_cnt_start_cmd_shift     = 0,
+	.perf_cnt_continuous_shift    = 2,
+	.perf_client_sel_shift        = 8,
+	.perf_window_start_shift      = 16,
+	.perf_window_end_shift        = 20,
+	.ai_c_srl_en_shift            = 11,
+	.ds16_c_srl_en_shift          = 10,
+	.ds4_c_srl_en_shift           = 9,
+};
+
+static struct cam_tfe_rdi_reg  tfe770_rdi0_reg = {
+	.rdi_hw_version              = 0x00001E00,
+	.rdi_hw_status               = 0x00001E04,
+	.rdi_module_config           = 0x00001E60,
+	.rdi_skip_period             = 0x00001E68,
+	.rdi_irq_subsample_pattern   = 0x00001E6C,
+	.rdi_epoch_irq               = 0x00001E70,
+	.rdi_debug_1                 = 0x00001FF0,
+	.rdi_debug_0                 = 0x00001FF4,
+	.rdi_test_bus_ctrl           = 0x00001FF8,
+	.rdi_spare                   = 0x00001FFC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_rdi_reg_data tfe770_rdi0_reg_data = {
+	.reg_update_cmd_data         = 0x2,
+	.epoch_line_cfg              = 0x00140014,
+	.pixel_pattern_shift         = 24,
+	.pixel_pattern_mask          = 0x07000000,
+	.rdi_out_enable_shift        = 0,
+
+	.sof_irq_mask                = 0x00000010,
+	.epoch0_irq_mask             = 0x00000040,
+	.epoch1_irq_mask             = 0x00000080,
+	.eof_irq_mask                = 0x00000020,
+	.error_irq_mask0             = 0x00020200,
+	.error_irq_mask2             = 0x00000004,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00000030,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x1,
+	.diag_sensor_shift           = 0x1,
+};
+
+static struct cam_tfe_rdi_reg  tfe770_rdi1_reg = {
+	.rdi_hw_version              = 0x00002000,
+	.rdi_hw_status               = 0x00002004,
+	.rdi_module_config           = 0x00002060,
+	.rdi_skip_period             = 0x00002068,
+	.rdi_irq_subsample_pattern   = 0x0000206C,
+	.rdi_epoch_irq               = 0x00002070,
+	.rdi_debug_1                 = 0x000021F0,
+	.rdi_debug_0                 = 0x000021F4,
+	.rdi_test_bus_ctrl           = 0x000021F8,
+	.rdi_spare                   = 0x000021FC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_rdi_reg_data tfe770_rdi1_reg_data = {
+	.reg_update_cmd_data         = 0x4,
+	.epoch_line_cfg              = 0x00140014,
+	.pixel_pattern_shift         = 24,
+	.pixel_pattern_mask          = 0x07000000,
+	.rdi_out_enable_shift        = 0,
+
+	.sof_irq_mask                = 0x00000100,
+	.epoch0_irq_mask             = 0x00000400,
+	.epoch1_irq_mask             = 0x00000800,
+	.eof_irq_mask                = 0x00000200,
+	.error_irq_mask0             = 0x00040400,
+	.error_irq_mask2             = 0x00000008,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00000300,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x2,
+	.diag_sensor_shift           = 0x1,
+};
+
+static struct cam_tfe_rdi_reg  tfe770_rdi2_reg = {
+	.rdi_hw_version              = 0x00002200,
+	.rdi_hw_status               = 0x00002204,
+	.rdi_module_config           = 0x00002260,
+	.rdi_skip_period             = 0x00002268,
+	.rdi_irq_subsample_pattern   = 0x0000226C,
+	.rdi_epoch_irq               = 0x00002270,
+	.rdi_debug_1                 = 0x000023F0,
+	.rdi_debug_0                 = 0x000023F4,
+	.rdi_test_bus_ctrl           = 0x000023F8,
+	.rdi_spare                   = 0x000023FC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_rdi_reg_data tfe770_rdi2_reg_data = {
+	.reg_update_cmd_data         = 0x8,
+	.epoch_line_cfg              = 0x00140014,
+	.pixel_pattern_shift         = 24,
+	.pixel_pattern_mask          = 0x07000000,
+	.rdi_out_enable_shift        = 0,
+
+	.sof_irq_mask                = 0x00001000,
+	.epoch0_irq_mask             = 0x00004000,
+	.epoch1_irq_mask             = 0x00008000,
+	.eof_irq_mask                = 0x00002000,
+	.error_irq_mask0             = 0x00080800,
+	.error_irq_mask2             = 0x00000004,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00003000,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x3,
+	.diag_sensor_shift           = 0x1,
+
+};
+
+static struct cam_tfe_ppp_reg  tfe770_ppp_reg = {
+	.ppp_hw_version              = 0x00002400,
+	.ppp_hw_status               = 0x00002404,
+	.ppp_module_config           = 0x00002460,
+	.ppp_skip_period             = 0x00002468,
+	.ppp_irq_subsample_pattern   = 0x0000246C,
+	.ppp_epoch_irq               = 0x00002470,
+	.ppp_debug_1                 = 0x000025F0,
+	.ppp_debug_0                 = 0x000025F4,
+	.ppp_test_bus_ctrl           = 0x000025F8,
+	.ppp_spare                   = 0x000025FC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_ppp_reg_data tfe770_ppp_reg_data = {
+	.sof_irq_mask                = 0x00000000,
+	.epoch0_irq_mask             = 0x00000000,
+	.epoch1_irq_mask             = 0x00000000,
+	.eof_irq_mask                = 0x00000000,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00000000,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x4,
+	.diag_sensor_shift           = 0x1,
+	.pdaf_path_en_shift          = 24,
+	.lcr_dis_en_shift            = 23,
+};
+
+static struct cam_tfe_clc_hw_status  tfe770_clc_hw_info[CAM_TFE_MAX_CLC] = {
+	{
+		.name = "CLC_CAMIF",
+		.hw_status_reg = 0x1C04,
+	},
+	{
+		.name = "CLC_RDI0_CAMIF",
+		.hw_status_reg = 0x1E04,
+	},
+	{
+		.name = "CLC_RDI1_CAMIF",
+		.hw_status_reg = 0x2004,
+	},
+	{
+		.name = "CLC_RDI2_CAMIF",
+		.hw_status_reg = 0x2204,
+	},
+	{
+		.name = "CLC_PD_CAMIF",
+		.hw_status_reg = 0x2404,
+	},
+	{
+		.name = "CLC_PDAF_LITE",
+		.hw_status_reg = 0x2A04,
+	},
+	{
+		.name = "CLC_CHANNEL_GAIN",
+		.hw_status_reg = 0x6004,
+	},
+	{
+		.name = "CLC_BPC_PDPC",
+		.hw_status_reg = 0x6204,
+	},
+	{
+		.name = "CLC_LCS",
+		.hw_status_reg = 0x6404,
+	},
+	{
+		.name = "CLC_SHARED_LB",
+		.hw_status_reg = 0x6604,
+	},
+	{
+		.name = "CLC_WB_BDS",
+		.hw_status_reg = 0x6804,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_POST_BDS",
+		.hw_status_reg = 0x6A04,
+	},
+	{
+		.name = "CLC_BLS",
+		.hw_status_reg = 0x6C04,
+	},
+	{
+		.name = "CLC_BAYER_GLUT",
+		.hw_status_reg = 0x6E04,
+	},
+	{
+		.name = "CLC_BAYER_DS4",
+		.hw_status_reg = 0x7004,
+	},
+	{
+		.name = "CLC_COLOR_XFORM_DS4",
+		.hw_status_reg = 0x7204,
+	},
+	{
+		.name = "CLC_CHROMA_DS2",
+		.hw_status_reg = 0x7404,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_Y_DS4",
+		.hw_status_reg = 0x7604,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_C_DS4",
+		.hw_status_reg = 0x7804,
+	},
+	{
+		.name = "CLC_R2PD_DS4",
+		.hw_status_reg = 0x7A04,
+	},
+	{
+		.name = "CLC_DOWNSCALE_4TO1_Y",
+		.hw_status_reg = 0x7C04,
+	},
+	{
+		.name = "CLC_DOWNSCALE_4TO1_C",
+		.hw_status_reg = 0x7E04,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_Y_DS16",
+		.hw_status_reg = 0x8004,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_C_DS16",
+		.hw_status_reg = 0x8204,
+	},
+	{
+		.name = "CLC_R2PD_DS16",
+		.hw_status_reg = 0x8404,
+	},
+	{
+		.name = "CLC_WB_GAIN",
+		.hw_status_reg = 0x8604,
+	},
+	{
+		.name = "CLC_BAYER_DS2",
+		.hw_status_reg = 0x8804,
+	},
+	{
+		.name = "CLC_GTM",
+		.hw_status_reg = 0x8A04,
+	},
+	{
+		.name = "CLC_COLOR_XFORM_AI_DS",
+		.hw_status_reg = 0x8C04,
+	},
+	{
+		.name = "CLC_DOWNSCALE_MN_Y",
+		.hw_status_reg = 0x8E04,
+	},
+	{
+		.name = "CLC_DOWNSCALE_MN_C",
+		.hw_status_reg = 0x9004,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_Y_AI_DS",
+		.hw_status_reg = 0x9204,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_C_AI_DS",
+		.hw_status_reg = 0x9404,
+	},
+	{
+		.name = "CLC_CROP_RND_CLAMP_IDEAL_RAW",
+		.hw_status_reg = 0x9604,
+	},
+	{
+		.name = "CLC_ABF",
+		.hw_status_reg = 0x9804,
+	},
+	{
+		.name = "CLC_STATS_BG",
+		.hw_status_reg = 0x9A04,
+	},
+	{
+		.name = "CLC_STATS_BHIST",
+		.hw_status_reg = 0x9C04,
+	},
+	{
+		.name = "CLC_STATS_AWB_BG",
+		.hw_status_reg = 0x9E04,
+	},
+	{
+		.name = "CLC_STATS_AEC_BG",
+		.hw_status_reg = 0xA004,
+	},
+	{
+		.name = "CLC_STATS_BAF",
+		.hw_status_reg = 0xA204,
+	},
+	{
+		.name = "CLC_STATS_RS",
+		.hw_status_reg = 0xA404,
+	},
+};
+
+static struct  cam_tfe_top_hw_info tfe770_top_hw_info = {
+	.common_reg = &tfe770_top_commong_reg,
+	.camif_hw_info = {
+		.camif_reg = &tfe770_camif_reg,
+		.reg_data  = &tfe770_camif_reg_data,
+	},
+	.rdi_hw_info  = {
+		{
+			.rdi_reg  = &tfe770_rdi0_reg,
+			.reg_data = &tfe770_rdi0_reg_data,
+		},
+		{
+			.rdi_reg  = &tfe770_rdi1_reg,
+			.reg_data = &tfe770_rdi1_reg_data,
+		},
+		{
+			.rdi_reg  = &tfe770_rdi2_reg,
+			.reg_data = &tfe770_rdi2_reg_data,
+		},
+	},
+	.ppp_hw_info = {
+		.ppp_reg = &tfe770_ppp_reg,
+		.reg_data  = &tfe770_ppp_reg_data,
+	},
+	.in_port = {
+		CAM_TFE_CAMIF_VER_1_0,
+		CAM_TFE_RDI_VER_1_0,
+		CAM_TFE_RDI_VER_1_0,
+		CAM_TFE_RDI_VER_1_0,
+		CAM_TFE_PDLIB_VER_1_0
+	},
+	.reg_dump_data  = {
+		.num_reg_dump_entries    = 19,
+		.num_lut_dump_entries    = 0,
+		.bus_start_addr          = 0x2000,
+		.bus_write_top_end_addr  = 0x2120,
+		.bus_client_start_addr   = 0x2200,
+		.bus_client_offset       = 0x100,
+		.num_bus_clients         = 10,
+		.reg_entry = {
+			{
+				.start_offset = 0x1000,
+				.end_offset   = 0x10F4,
+			},
+			{
+				.start_offset = 0x1260,
+				.end_offset   = 0x1280,
+			},
+			{
+				.start_offset = 0x13F0,
+				.end_offset   = 0x13FC,
+			},
+			{
+				.start_offset = 0x1460,
+				.end_offset   = 0x1470,
+			},
+			{
+				.start_offset = 0x15F0,
+				.end_offset   = 0x15FC,
+			},
+			{
+				.start_offset = 0x1660,
+				.end_offset   = 0x1670,
+			},
+			{
+				.start_offset = 0x17F0,
+				.end_offset   = 0x17FC,
+			},
+			{
+				.start_offset = 0x1860,
+				.end_offset   = 0x1870,
+			},
+			{
+				.start_offset = 0x19F0,
+				.end_offset   = 0x19FC,
+			},
+			{
+				.start_offset = 0x2660,
+				.end_offset   = 0x2694,
+			},
+			{
+				.start_offset = 0x2860,
+				.end_offset   = 0x2884,
+			},
+			{
+				.start_offset = 0x2A60,
+				.end_offset   = 0X2B34,
+			},
+			{
+				.start_offset = 0x2C60,
+				.end_offset   = 0X2C80,
+			},
+			{
+				.start_offset = 0x2E60,
+				.end_offset   = 0X2E7C,
+			},
+			{
+				.start_offset = 0x3060,
+				.end_offset   = 0X3110,
+			},
+			{
+				.start_offset = 0x3260,
+				.end_offset   = 0X3278,
+			},
+			{
+				.start_offset = 0x3460,
+				.end_offset   = 0X3478,
+			},
+			{
+				.start_offset = 0x3660,
+				.end_offset   = 0X3684,
+			},
+			{
+				.start_offset = 0x3860,
+				.end_offset   = 0X3884,
+			},
+		},
+		.lut_entry = {
+			{
+				.lut_word_size = 1,
+				.lut_bank_sel  = 0x40,
+				.lut_addr_size = 180,
+				.dmi_reg_offset = 0x2800,
+			},
+			{
+				.lut_word_size = 1,
+				.lut_bank_sel  = 0x41,
+				.lut_addr_size = 180,
+				.dmi_reg_offset = 0x3000,
+			},
+		},
+	},
+	.num_path_port_map = 3,
+	.path_port_map = {
+		{CAM_ISP_HW_TFE_IN_PDLIB, CAM_ISP_TFE_OUT_RES_PD_LCR_STATS},
+		{CAM_ISP_HW_TFE_IN_PDLIB, CAM_ISP_TFE_OUT_RES_PD_PREPROCESSED},
+		{CAM_ISP_HW_TFE_IN_PDLIB, CAM_ISP_TFE_OUT_RES_PD_PARSED},
+	},
+};
+
+static struct cam_tfe_bus_hw_info  tfe770_bus_hw_info = {
+	.common_reg = {
+		.hw_version  = 0x00003000,
+		.cgc_ovd     = 0x00003008,
+		.comp_cfg_0  = 0x0000300C,
+		.comp_cfg_1  = 0x00003010,
+		.frameheader_cfg  = {
+			0x00003034,
+			0x00003038,
+			0x0000303C,
+			0x00003040,
+		},
+		.pwr_iso_cfg = 0x0000305C,
+		.overflow_status_clear = 0x00003060,
+		.ccif_violation_status = 0x00003064,
+		.overflow_status       = 0x00003068,
+		.image_size_violation_status = 0x00003070,
+		.perf_count_cfg = {
+			0x00003074,
+			0x00003078,
+			0x0000307C,
+			0x00003080,
+			0x00003084,
+			0x00003088,
+			0x0000308C,
+			0x00003090,
+		},
+		.perf_count_val = {
+			0x00003094,
+			0x00003098,
+			0x0000309C,
+			0x000030A0,
+			0x000030A4,
+			0x000030A8,
+			0x000030AC,
+			0x000030B0,
+		},
+		.perf_count_status = 0x000030B4,
+		.debug_status_top_cfg = 0x000030D4,
+		.debug_status_top = 0x000030D8,
+		.test_bus_ctrl = 0x000030DC,
+		.irq_mask = {
+			0x00003018,
+			0x0000301C,
+		},
+		.irq_clear = {
+			0x00003020,
+			0x00003024,
+		},
+		.irq_status = {
+			0x00003028,
+			0x0000302C,
+		},
+		.irq_cmd = 0x00003030,
+		.cons_violation_shift = 28,
+		.violation_shift  = 30,
+		.image_size_violation = 31,
+	},
+	.num_client = 19,
+	.bus_client_reg = {
+		/* BUS Client 0 BAYER */
+		{
+			.cfg                   = 0x00003200,
+			.image_addr            = 0x00003204,
+			.frame_incr            = 0x00003208,
+			.image_cfg_0           = 0x0000320C,
+			.image_cfg_1           = 0x00003210,
+			.image_cfg_2           = 0x00003214,
+			.packer_cfg            = 0x00003218,
+			.bw_limit              = 0x0000321C,
+			.frame_header_addr     = 0x00003220,
+			.frame_header_incr     = 0x00003224,
+			.frame_header_cfg      = 0x00003228,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003230,
+			.irq_subsample_pattern = 0x00003234,
+			.framedrop_period      = 0x00003238,
+			.framedrop_pattern     = 0x0000323C,
+			.system_cache_cfg      = 0x00003260,
+			.addr_status_0         = 0x00003268,
+			.addr_status_1         = 0x0000326C,
+			.addr_status_2         = 0x00003270,
+			.addr_status_3         = 0x00003274,
+			.debug_status_cfg      = 0x00003278,
+			.debug_status_0        = 0x0000327C,
+			.debug_status_1        = 0x00003280,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_0,
+			.client_name           = "BAYER",
+		},
+		/* BUS Client 1 IDEAL RAW*/
+		{
+			.cfg                   = 0x00003300,
+			.image_addr            = 0x00003304,
+			.frame_incr            = 0x00003308,
+			.image_cfg_0           = 0x0000330C,
+			.image_cfg_1           = 0x00003310,
+			.image_cfg_2           = 0x00003314,
+			.packer_cfg            = 0x00003318,
+			.bw_limit              = 0x0000331C,
+			.frame_header_addr     = 0x00003320,
+			.frame_header_incr     = 0x00003324,
+			.frame_header_cfg      = 0x00003328,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003330,
+			.irq_subsample_pattern = 0x00003334,
+			.framedrop_period      = 0x00003338,
+			.framedrop_pattern     = 0x0000333C,
+			.system_cache_cfg      = 0x00003360,
+			.addr_status_0         = 0x00003368,
+			.addr_status_1         = 0x0000336C,
+			.addr_status_2         = 0x00003370,
+			.addr_status_3         = 0x00003374,
+			.debug_status_cfg      = 0x00003378,
+			.debug_status_0        = 0x0000337C,
+			.debug_status_1        = 0x00003380,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_1,
+			.client_name           = "IDEAL_RAW",
+		},
+		/* BUS Client 2 Stats BE Tintless */
+		{
+			.cfg                   = 0x00003400,
+			.image_addr            = 0x00003404,
+			.frame_incr            = 0x00003408,
+			.image_cfg_0           = 0x0000340C,
+			.image_cfg_1           = 0x00003410,
+			.image_cfg_2           = 0x00003414,
+			.packer_cfg            = 0x00003418,
+			.bw_limit              = 0x0000341C,
+			.frame_header_addr     = 0x00003420,
+			.frame_header_incr     = 0x00003424,
+			.frame_header_cfg      = 0x00003428,
+			.line_done_cfg         = 0x00003400,
+			.irq_subsample_period  = 0x00003430,
+			.irq_subsample_pattern = 0x00003434,
+			.framedrop_period      = 0x00003438,
+			.framedrop_pattern     = 0x0000343C,
+			.system_cache_cfg      = 0x00003460,
+			.addr_status_0         = 0x00003468,
+			.addr_status_1         = 0x0000346C,
+			.addr_status_2         = 0x00003470,
+			.addr_status_3         = 0x00003474,
+			.debug_status_cfg      = 0x00003478,
+			.debug_status_0        = 0x0000347C,
+			.debug_status_1        = 0x00003480,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_2,
+			.client_name           = "STATS BE TINTLESS",
+		},
+		/* BUS Client 3 Stats Bhist */
+		{
+			.cfg                   = 0x00003500,
+			.image_addr            = 0x00003504,
+			.frame_incr            = 0x00003508,
+			.image_cfg_0           = 0x0000350C,
+			.image_cfg_1           = 0x00003510,
+			.image_cfg_2           = 0x00003514,
+			.packer_cfg            = 0x00003518,
+			.bw_limit              = 0x0000351C,
+			.frame_header_addr     = 0x00003520,
+			.frame_header_incr     = 0x00003524,
+			.frame_header_cfg      = 0x00003528,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003530,
+			.irq_subsample_pattern = 0x00003534,
+			.framedrop_period      = 0x00003538,
+			.framedrop_pattern     = 0x0000353C,
+			.system_cache_cfg      = 0x00003560,
+			.addr_status_0         = 0x00003568,
+			.addr_status_1         = 0x0000356C,
+			.addr_status_2         = 0x00003570,
+			.addr_status_3         = 0x00003574,
+			.debug_status_cfg      = 0x00003578,
+			.debug_status_0        = 0x0000357C,
+			.debug_status_1        = 0x00003580,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_2,
+			.client_name           = "STATS BHIST",
+		},
+		/* BUS Client 4 Stats AWB BG */
+		{
+			.cfg                   = 0x00003600,
+			.image_addr            = 0x00003604,
+			.frame_incr            = 0x00003608,
+			.image_cfg_0           = 0x0000360C,
+			.image_cfg_1           = 0x00003610,
+			.image_cfg_2           = 0x00003614,
+			.packer_cfg            = 0x00003618,
+			.bw_limit              = 0x0000361C,
+			.frame_header_addr     = 0x00003620,
+			.frame_header_incr     = 0x00003624,
+			.frame_header_cfg      = 0x00003628,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003630,
+			.irq_subsample_pattern = 0x00003634,
+			.framedrop_period      = 0x00003638,
+			.framedrop_pattern     = 0x0000363C,
+			.system_cache_cfg      = 0x00003660,
+			.addr_status_0         = 0x00003668,
+			.addr_status_1         = 0x0000366C,
+			.addr_status_2         = 0x00003670,
+			.addr_status_3         = 0x00003674,
+			.debug_status_cfg      = 0x00003678,
+			.debug_status_0        = 0x0000367C,
+			.debug_status_1        = 0x00003680,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_3,
+			.client_name           = "STATS AWB BG",
+		},
+		/* BUS Client 5 Stats AEC BG */
+		{
+			.cfg                   = 0x00003700,
+			.image_addr            = 0x00003704,
+			.frame_incr            = 0x00003708,
+			.image_cfg_0           = 0x0000370C,
+			.image_cfg_1           = 0x00003710,
+			.image_cfg_2           = 0x00003714,
+			.packer_cfg            = 0x00003718,
+			.bw_limit              = 0x0000371C,
+			.frame_header_addr     = 0x00003720,
+			.frame_header_incr     = 0x00003724,
+			.frame_header_cfg      = 0x00003728,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003730,
+			.irq_subsample_pattern = 0x00003734,
+			.framedrop_period      = 0x00003738,
+			.framedrop_pattern     = 0x0000373C,
+			.system_cache_cfg      = 0x00003760,
+			.addr_status_0         = 0x00003768,
+			.addr_status_1         = 0x0000376C,
+			.addr_status_2         = 0x00003770,
+			.addr_status_3         = 0x00003774,
+			.debug_status_cfg      = 0x00003778,
+			.debug_status_0        = 0x0000377C,
+			.debug_status_1        = 0x00003780,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_3,
+			.client_name           = "STATS AEC BG",
+		},
+		/* BUS Client 6 Stats BAF */
+		{
+			.cfg                   = 0x00003800,
+			.image_addr            = 0x00003804,
+			.frame_incr            = 0x00003808,
+			.image_cfg_0           = 0x0000380C,
+			.image_cfg_1           = 0x00003810,
+			.image_cfg_2           = 0x00003814,
+			.packer_cfg            = 0x00003818,
+			.bw_limit              = 0x0000381C,
+			.frame_header_addr     = 0x00003820,
+			.frame_header_incr     = 0x00003824,
+			.frame_header_cfg      = 0x00003828,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003830,
+			.irq_subsample_pattern = 0x00003834,
+			.framedrop_period      = 0x00003838,
+			.framedrop_pattern     = 0x0000383C,
+			.system_cache_cfg      = 0x00003860,
+			.addr_status_0         = 0x00003868,
+			.addr_status_1         = 0x0000386C,
+			.addr_status_2         = 0x00003870,
+			.addr_status_3         = 0x00003874,
+			.debug_status_cfg      = 0x00003878,
+			.debug_status_0        = 0x0000387C,
+			.debug_status_1        = 0x00003880,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_4,
+			.client_name           = "STATS BAF",
+		},
+		/* BUS Client 7 RDI0 */
+		{
+			.cfg                   = 0x00003900,
+			.image_addr            = 0x00003904,
+			.frame_incr            = 0x00003908,
+			.image_cfg_0           = 0x0000390C,
+			.image_cfg_1           = 0x00003910,
+			.image_cfg_2           = 0x00003914,
+			.packer_cfg            = 0x00003918,
+			.bw_limit              = 0x0000391C,
+			.frame_header_addr     = 0x00003920,
+			.frame_header_incr     = 0x00003924,
+			.frame_header_cfg      = 0x00003928,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003930,
+			.irq_subsample_pattern = 0x00003934,
+			.framedrop_period      = 0x00003938,
+			.framedrop_pattern     = 0x0000393C,
+			.system_cache_cfg      = 0x00003960,
+			.addr_status_0         = 0x00003968,
+			.addr_status_1         = 0x0000396C,
+			.addr_status_2         = 0x00003970,
+			.addr_status_3         = 0x00003974,
+			.debug_status_cfg      = 0x00003978,
+			.debug_status_0        = 0x0000397C,
+			.debug_status_1        = 0x00003980,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_5,
+			.client_name           = "RDI0",
+		},
+		/* BUS Client 8 RDI1 */
+		{
+			.cfg                   = 0x00003A00,
+			.image_addr            = 0x00003A04,
+			.frame_incr            = 0x00003A08,
+			.image_cfg_0           = 0x00003A0C,
+			.image_cfg_1           = 0x00003A10,
+			.image_cfg_2           = 0x00003A14,
+			.packer_cfg            = 0x00003A18,
+			.bw_limit              = 0x00003A1C,
+			.frame_header_addr     = 0x00003A20,
+			.frame_header_incr     = 0x00003A24,
+			.frame_header_cfg      = 0x00003A28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003A30,
+			.irq_subsample_pattern = 0x00003A34,
+			.framedrop_period      = 0x00003A38,
+			.framedrop_pattern     = 0x00003A3C,
+			.system_cache_cfg      = 0x00003A60,
+			.addr_status_0         = 0x00003A68,
+			.addr_status_1         = 0x00003A6C,
+			.addr_status_2         = 0x00003A70,
+			.addr_status_3         = 0x00003A74,
+			.debug_status_cfg      = 0x00003A78,
+			.debug_status_0        = 0x00003A7C,
+			.debug_status_1        = 0x00003A80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_6,
+			.client_name           = "RDI1",
+		},
+		/* BUS Client 9 RDI2 */
+		{
+			.cfg                   = 0x00003B00,
+			.image_addr            = 0x00003B04,
+			.frame_incr            = 0x00003B08,
+			.image_cfg_0           = 0x00003B0C,
+			.image_cfg_1           = 0x00003B10,
+			.image_cfg_2           = 0x00003B14,
+			.packer_cfg            = 0x00003B18,
+			.bw_limit              = 0x00003B1C,
+			.frame_header_addr     = 0x00003B20,
+			.frame_header_incr     = 0x00003B24,
+			.frame_header_cfg      = 0x00003B28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003B30,
+			.irq_subsample_pattern = 0x00003B34,
+			.framedrop_period      = 0x00003B38,
+			.framedrop_pattern     = 0x00003B3C,
+			.system_cache_cfg      = 0x00003B60,
+			.addr_status_0         = 0x00003B68,
+			.addr_status_1         = 0x00003B6C,
+			.addr_status_2         = 0x00003B70,
+			.addr_status_3         = 0x00003B74,
+			.debug_status_cfg      = 0x00003B78,
+			.debug_status_0        = 0x00003B7C,
+			.debug_status_1        = 0x00003B80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_7,
+			.client_name           = "RDI2",
+		},
+		/* BUS Client 10 PDAF */
+		{
+			.cfg                   = 0x00003C00,
+			.image_addr            = 0x00003C04,
+			.frame_incr            = 0x00003C08,
+			.image_cfg_0           = 0x00003C0C,
+			.image_cfg_1           = 0x00003C10,
+			.image_cfg_2           = 0x00003C14,
+			.packer_cfg            = 0x00003C18,
+			.bw_limit              = 0x00003C1C,
+			.frame_header_addr     = 0x00003C20,
+			.frame_header_incr     = 0x00003C24,
+			.frame_header_cfg      = 0x00003C28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003C30,
+			.irq_subsample_pattern = 0x00003C34,
+			.framedrop_period      = 0x00003C38,
+			.framedrop_pattern     = 0x00003C3C,
+			.system_cache_cfg      = 0x00003C60,
+			.addr_status_0         = 0x00003C68,
+			.addr_status_1         = 0x00003C6C,
+			.addr_status_2         = 0x00003C70,
+			.addr_status_3         = 0x00003C74,
+			.debug_status_cfg      = 0x00003C78,
+			.debug_status_0        = 0x00003C7C,
+			.debug_status_1        = 0x00003C80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_8,
+			.client_name           = "PDAF",
+		},
+		/* BUS Client 11 DS4 */
+		{
+			.cfg                   = 0x00003D00,
+			.image_addr            = 0x00003D04,
+			.frame_incr            = 0x00003D08,
+			.image_cfg_0           = 0x00003D0C,
+			.image_cfg_1           = 0x00003D10,
+			.image_cfg_2           = 0x00003D14,
+			.packer_cfg            = 0x00003D18,
+			.bw_limit              = 0x00003D1C,
+			.frame_header_addr     = 0x00003D20,
+			.frame_header_incr     = 0x00003D24,
+			.frame_header_cfg      = 0x00003D28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003D30,
+			.irq_subsample_pattern = 0x00003D34,
+			.framedrop_period      = 0x00003D38,
+			.framedrop_pattern     = 0x00003D3C,
+			.system_cache_cfg      = 0x00003D60,
+			.addr_status_0         = 0x00003D68,
+			.addr_status_1         = 0x00003D6C,
+			.addr_status_2         = 0x00003D70,
+			.addr_status_3         = 0x00003D74,
+			.debug_status_cfg      = 0x00003D78,
+			.debug_status_0        = 0x00003D7C,
+			.debug_status_1        = 0x00003D80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_0,
+			.client_name           = "DS4",
+		},
+		/* BUS Client 12 DS16 */
+		{
+			.cfg                   = 0x00003E00,
+			.image_addr            = 0x00003E04,
+			.frame_incr            = 0x00003E08,
+			.image_cfg_0           = 0x00003E0C,
+			.image_cfg_1           = 0x00003E10,
+			.image_cfg_2           = 0x00003E14,
+			.packer_cfg            = 0x00003E18,
+			.bw_limit              = 0x00003E1C,
+			.frame_header_addr     = 0x00003E20,
+			.frame_header_incr     = 0x00003E24,
+			.frame_header_cfg      = 0x00003E28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003E30,
+			.irq_subsample_pattern = 0x00003E34,
+			.framedrop_period      = 0x00003E38,
+			.framedrop_pattern     = 0x00003E3C,
+			.system_cache_cfg      = 0x00003E60,
+			.addr_status_0         = 0x00003E68,
+			.addr_status_1         = 0x00003E6C,
+			.addr_status_2         = 0x00003E70,
+			.addr_status_3         = 0x00003E74,
+			.debug_status_cfg      = 0x00003E78,
+			.debug_status_0        = 0x00003E7C,
+			.debug_status_1        = 0x00003E80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_0,
+			.client_name           = "DS16",
+		},
+		/* BUS Client 13 AI-Y */
+		{
+			.cfg                   = 0x00003F00,
+			.image_addr            = 0x00003F04,
+			.frame_incr            = 0x00003F08,
+			.image_cfg_0           = 0x00003F0C,
+			.image_cfg_1           = 0x00003F10,
+			.image_cfg_2           = 0x00003F14,
+			.packer_cfg            = 0x00003F18,
+			.bw_limit              = 0x00003F1C,
+			.frame_header_addr     = 0x00003F20,
+			.frame_header_incr     = 0x00003F24,
+			.frame_header_cfg      = 0x00003F28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003F30,
+			.irq_subsample_pattern = 0x00003F34,
+			.framedrop_period      = 0x00003F38,
+			.framedrop_pattern     = 0x00003F3C,
+			.system_cache_cfg      = 0x00003F60,
+			.addr_status_0         = 0x00003F68,
+			.addr_status_1         = 0x00003F6C,
+			.addr_status_2         = 0x00003F70,
+			.addr_status_3         = 0x00003F74,
+			.debug_status_cfg      = 0x00003F78,
+			.debug_status_0        = 0x00003F7C,
+			.debug_status_1        = 0x00003F80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_9,
+			.client_name           = "AI-Y",
+		},
+		/* BUS Client 14 AI-C */
+		{
+			.cfg                   = 0x00004000,
+			.image_addr            = 0x00004004,
+			.frame_incr            = 0x00004008,
+			.image_cfg_0           = 0x0000400C,
+			.image_cfg_1           = 0x00004010,
+			.image_cfg_2           = 0x00004014,
+			.packer_cfg            = 0x00004018,
+			.bw_limit              = 0x0000401C,
+			.frame_header_addr     = 0x00004020,
+			.frame_header_incr     = 0x00004024,
+			.frame_header_cfg      = 0x00004028,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00004030,
+			.irq_subsample_pattern = 0x00004034,
+			.framedrop_period      = 0x00004038,
+			.framedrop_pattern     = 0x0000403C,
+			.system_cache_cfg      = 0x00004060,
+			.addr_status_0         = 0x00004068,
+			.addr_status_1         = 0x0000406C,
+			.addr_status_2         = 0x00004070,
+			.addr_status_3         = 0x00004074,
+			.debug_status_cfg      = 0x00004078,
+			.debug_status_0        = 0x0000407C,
+			.debug_status_1        = 0x00004080,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_9,
+			.client_name           = "AI-C",
+		},
+		/* BUS Client 15 Stats RS */
+		{
+			.cfg                   = 0x00004100,
+			.image_addr            = 0x00004104,
+			.frame_incr            = 0x00004108,
+			.image_cfg_0           = 0x0000410C,
+			.image_cfg_1           = 0x00004110,
+			.image_cfg_2           = 0x00004114,
+			.packer_cfg            = 0x00004118,
+			.bw_limit              = 0x0000411C,
+			.frame_header_addr     = 0x00004120,
+			.frame_header_incr     = 0x00004124,
+			.frame_header_cfg      = 0x00004128,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00004130,
+			.irq_subsample_pattern = 0x00004134,
+			.framedrop_period      = 0x00004138,
+			.framedrop_pattern     = 0x0000413C,
+			.system_cache_cfg      = 0x00004160,
+			.addr_status_0         = 0x00004168,
+			.addr_status_1         = 0x0000416C,
+			.addr_status_2         = 0x00004170,
+			.addr_status_3         = 0x00004174,
+			.debug_status_cfg      = 0x00004178,
+			.debug_status_0        = 0x0000417C,
+			.debug_status_1        = 0x00004180,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_10,
+			.client_name           = "STATS RS",
+		},
+		/* BUS Client 16 PDAF 0 STAT LCR */
+		{
+			.cfg                   = 0x00004200,
+			.image_addr            = 0x00004204,
+			.frame_incr            = 0x00004208,
+			.image_cfg_0           = 0x0000420C,
+			.image_cfg_1           = 0x00004210,
+			.image_cfg_2           = 0x00004214,
+			.packer_cfg            = 0x00004218,
+			.bw_limit              = 0x0000421C,
+			.frame_header_addr     = 0x00004220,
+			.frame_header_incr     = 0x00004224,
+			.frame_header_cfg      = 0x00004228,
+			.line_done_cfg         = 0x0000422C,
+			.irq_subsample_period  = 0x00004230,
+			.irq_subsample_pattern = 0x00004234,
+			.framedrop_period      = 0x00004238,
+			.framedrop_pattern     = 0x0000423C,
+			.system_cache_cfg      = 0x00004260,
+			.addr_status_0         = 0x00004268,
+			.addr_status_1         = 0x0000426C,
+			.addr_status_2         = 0x00004270,
+			.addr_status_3         = 0x00004274,
+			.debug_status_cfg      = 0x00004278,
+			.debug_status_0        = 0x0000427C,
+			.debug_status_1        = 0x00004280,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_11,
+			.client_name           = "STAT LCR",
+		},
+		/* BUS Client 17 PDAF 1 PD PREPROCESSED*/
+		{
+			.cfg                   = 0x00004300,
+			.image_addr            = 0x00004304,
+			.frame_incr            = 0x00004308,
+			.image_cfg_0           = 0x0000430C,
+			.image_cfg_1           = 0x00004310,
+			.image_cfg_2           = 0x00004314,
+			.packer_cfg            = 0x00004318,
+			.bw_limit              = 0x0000431C,
+			.frame_header_addr     = 0x00004320,
+			.frame_header_incr     = 0x00004324,
+			.frame_header_cfg      = 0x00004328,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00004330,
+			.irq_subsample_pattern = 0x00004334,
+			.framedrop_period      = 0x00004338,
+			.framedrop_pattern     = 0x0000433C,
+			.system_cache_cfg      = 0x00004360,
+			.addr_status_0         = 0x00004368,
+			.addr_status_1         = 0x0000436C,
+			.addr_status_2         = 0x00004370,
+			.addr_status_3         = 0x00004374,
+			.debug_status_cfg      = 0x00004378,
+			.debug_status_0        = 0x0000437C,
+			.debug_status_1        = 0x00004380,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_11,
+			.client_name           = "PD PREPROCESSED",
+		},
+		/* BUS Client 18 PDAF 2 PD PARSED*/
+		{
+			.cfg                   = 0x00004400,
+			.image_addr            = 0x00004404,
+			.frame_incr            = 0x00004408,
+			.image_cfg_0           = 0x0000440C,
+			.image_cfg_1           = 0x00004410,
+			.image_cfg_2           = 0x00004414,
+			.packer_cfg            = 0x00004418,
+			.bw_limit              = 0x0000441C,
+			.frame_header_addr     = 0x00004420,
+			.frame_header_incr     = 0x00004424,
+			.frame_header_cfg      = 0x00004428,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00004430,
+			.irq_subsample_pattern = 0x00004434,
+			.framedrop_period      = 0x00004438,
+			.framedrop_pattern     = 0x0000443C,
+			.system_cache_cfg      = 0x00004460,
+			.addr_status_0         = 0x00004468,
+			.addr_status_1         = 0x0000446C,
+			.addr_status_2         = 0x00004470,
+			.addr_status_3         = 0x00004474,
+			.debug_status_cfg      = 0x00004478,
+			.debug_status_0        = 0x0000447C,
+			.debug_status_1        = 0x00004480,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_11,
+			.client_name           = "PD PARSED",
+		},
+	},
+	.num_out  = 18,
+	.tfe_out_hw_info = {
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RDI0,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_5,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_1,
+			.mid[0]              = 4,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RDI1,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_6,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_2,
+			.mid[0]              = 5,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RDI2,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_7,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_3,
+			.mid[0]              = 6,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_FULL,
+			.max_width        = 4096,
+			.max_height       = 4096,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_0,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 16,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RAW_DUMP,
+			.max_width        = 4096,
+			.max_height       = 4096,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_1,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 7,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_PDAF,
+			.max_width        = 4096,
+			.max_height       = 4096,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_8,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 26,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_STATS_HDR_BE,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_3,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 21,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_STATS_HDR_BHIST,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_2,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 18,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_STATS_TL_BG,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_2,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 17,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_STATS_AWB_BG,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_3,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 19,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_STATS_BF,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_4,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 21,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_STATS_RS,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_10,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 27,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_DS4,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_0,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 22,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_DS16,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_0,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 23,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_AI,
+			.max_width        = 1920,
+			.max_height       = 1920,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_9,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_0,
+			.mid[0]              = 24,
+			.mid[1]              = 25,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_PD_LCR_STATS,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_11,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_4,
+			.mid[0]           = 21,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_PD_PREPROCESSED,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_11,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_4,
+			.mid[0]           = 20,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_PD_PARSED,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_11,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_4,
+			.mid[0]           = 22,
+		},
+	},
+	.num_comp_grp             = 12,
+	.max_wm_per_comp_grp      = 3,
+	.comp_done_shift          = 8,
+	.top_bus_wr_irq_shift     = 1,
+	.comp_buf_done_mask = 0x7FF00,
+	.comp_rup_done_mask = 0xF,
+	.bus_irq_error_mask = {
+		0xD0000000,
+		0x00000000,
+	},
+	.support_consumed_addr = true,
+	.pdaf_rdi2_mux_en = false,
+	.rdi_width = 128,
+};
+
+struct cam_tfe_hw_info cam_tfe770 = {
+	.top_irq_mask = {
+		0x00001834,
+		0x00001838,
+		0x0000183C,
+	},
+	.top_irq_clear = {
+		0x00001840,
+		0x00001844,
+		0x00001848,
+	},
+	.top_irq_status = {
+		0x0000184C,
+		0x00001850,
+		0x00001854,
+	},
+	.top_irq_cmd                       = 0x00001830,
+	.global_clear_bitmask              = 0x00000001,
+	.bus_irq_mask = {
+		0x00003018,
+		0x0000301C,
+	},
+	.bus_irq_clear = {
+		0x00003020,
+		0x00003024,
+	},
+	.bus_irq_status = {
+		0x00003028,
+		0x0000302C,
+	},
+	.bus_irq_cmd = 0x00003030,
+	.bus_violation_reg = 0x00003064,
+	.bus_overflow_reg = 0x00003068,
+	.bus_image_size_vilation_reg = 0x3070,
+	.bus_overflow_clear_cmd = 0x3060,
+	.debug_status_top = 0x30D8,
+
+	.reset_irq_mask = {
+		0x00000001,
+		0x00000000,
+		0x00000000,
+	},
+	.error_irq_mask = {
+		0x001F1F00,
+		0x00000000,
+		0x000000FF,
+	},
+	.bus_reg_irq_mask = {
+		0x00000002,
+		0x00000000,
+	},
+	.bus_error_irq_mask = {
+		0xC0000000,
+		0x00000000,
+	},
+
+	.num_clc = 39,
+	.clc_hw_status_info            = tfe770_clc_hw_info,
+	.bus_version                   = CAM_TFE_BUS_1_0,
+	.bus_hw_info                   = &tfe770_bus_hw_info,
+
+	.top_version                   = CAM_TFE_TOP_1_0,
+	.top_hw_info                   = &tfe770_top_hw_info,
+};
+
+#endif /* _CAM_TFE770__H_ */

+ 161 - 18
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_bus.c

@@ -71,6 +71,8 @@ struct cam_tfe_bus_common_data {
 	uint32_t                                    num_sec_out;
 	uint32_t                                    comp_done_shift;
 	uint32_t                                    rdi_width;
+	uint32_t                                    en_cfg_shift;
+	uint32_t                                    height_shift;
 	bool                                        is_lite;
 	bool                                        support_consumed_addr;
 	cam_hw_mgr_event_cb_func                    event_cb;
@@ -79,6 +81,7 @@ struct cam_tfe_bus_common_data {
 	uint32_t                                    max_bw_counter_limit;
 	uint32_t                                    counter_limit_shift;
 	uint32_t                                    counter_limit_mask;
+	uint32_t                                    pack_align_shift;
 };
 
 struct cam_tfe_bus_wm_resource_data {
@@ -186,6 +189,9 @@ static bool cam_tfe_bus_can_be_secure(uint32_t out_id)
 	case CAM_TFE_BUS_TFE_OUT_DS4:
 	case CAM_TFE_BUS_TFE_OUT_DS16:
 	case CAM_TFE_BUS_TFE_OUT_AI:
+	case CAM_TFE_BUS_TFE_OUT_PD_LCR_STATS:
+	case CAM_TFE_BUS_TFE_OUT_PD_PREPROCESSED:
+	case CAM_TFE_BUS_TFE_OUT_PD_PARSED:
 		return true;
 
 	case CAM_TFE_BUS_TFE_OUT_STATS_HDR_BE:
@@ -233,6 +239,12 @@ static enum cam_tfe_bus_tfe_out_id
 		return CAM_TFE_BUS_TFE_OUT_DS16;
 	case CAM_ISP_TFE_OUT_RES_AI:
 		return CAM_TFE_BUS_TFE_OUT_AI;
+	case CAM_ISP_TFE_OUT_RES_PD_LCR_STATS:
+		return CAM_TFE_BUS_TFE_OUT_PD_LCR_STATS;
+	case CAM_ISP_TFE_OUT_RES_PD_PREPROCESSED:
+		return CAM_TFE_BUS_TFE_OUT_PD_PREPROCESSED;
+	case CAM_ISP_TFE_OUT_RES_PD_PARSED:
+		return CAM_TFE_BUS_TFE_OUT_PD_PARSED;
 	default:
 		return CAM_TFE_BUS_TFE_OUT_MAX;
 	}
@@ -350,6 +362,17 @@ static int cam_tfe_bus_get_num_wm(
 			break;
 		}
 		break;
+	case CAM_TFE_BUS_TFE_OUT_PD_LCR_STATS:
+	case CAM_TFE_BUS_TFE_OUT_PD_PREPROCESSED:
+	case CAM_TFE_BUS_TFE_OUT_PD_PARSED:
+		switch (format) {
+		case CAM_FORMAT_PLAIN16_16:
+		case CAM_FORMAT_PLAIN64:
+			return 1;
+		default:
+			break;
+		}
+		break;
 	default:
 		break;
 	}
@@ -360,6 +383,47 @@ static int cam_tfe_bus_get_num_wm(
 	return -EINVAL;
 }
 
+static int cam_tfe_lite_bus_get_wm_idx(
+	enum cam_tfe_bus_tfe_out_id tfe_out_res_id,
+	enum cam_tfe_bus_plane_type plane)
+{
+	int wm_idx = -1;
+
+	switch (tfe_out_res_id) {
+	case CAM_TFE_BUS_TFE_OUT_RDI0:
+		switch (plane) {
+		case PLANE_Y:
+			wm_idx = 0;
+			break;
+		default:
+			break;
+		}
+		break;
+	case CAM_TFE_BUS_TFE_OUT_RDI1:
+		switch (plane) {
+		case PLANE_Y:
+			wm_idx = 1;
+			break;
+		default:
+			break;
+		}
+		break;
+	case CAM_TFE_BUS_TFE_OUT_RDI2:
+		switch (plane) {
+		case PLANE_Y:
+			wm_idx = 2;
+			break;
+		default:
+			break;
+		}
+		break;
+	default:
+		break;
+	}
+
+	return wm_idx;
+}
+
 static int cam_tfe_bus_get_wm_idx(
 	enum cam_tfe_bus_tfe_out_id tfe_out_res_id,
 	enum cam_tfe_bus_plane_type plane,
@@ -510,6 +574,33 @@ static int cam_tfe_bus_get_wm_idx(
 			break;
 		}
 		break;
+	case CAM_TFE_BUS_TFE_OUT_PD_LCR_STATS:
+		switch (plane) {
+		case PLANE_Y:
+			wm_idx = 16;
+			break;
+		default:
+			break;
+		}
+		break;
+	case CAM_TFE_BUS_TFE_OUT_PD_PREPROCESSED:
+		switch (plane) {
+		case PLANE_Y:
+			wm_idx = 17;
+			break;
+		default:
+			break;
+		}
+		break;
+	case CAM_TFE_BUS_TFE_OUT_PD_PARSED:
+		switch (plane) {
+		case PLANE_Y:
+			wm_idx = 18;
+			break;
+		default:
+			break;
+		}
+		break;
 	default:
 		break;
 	}
@@ -561,7 +652,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 {
 	int pack_fmt = 0;
 	int rdi_width = rsrc_data->common_data->rdi_width;
-
+	int en_cfg_shift = rsrc_data->common_data->en_cfg_shift;
 	if (rdi_width == 64)
 		pack_fmt = 0xa;
 	else if (rdi_width == 128)
@@ -581,7 +672,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 	case CAM_FORMAT_MIPI_RAW_8:
@@ -598,7 +689,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 	case CAM_FORMAT_MIPI_RAW_10:
@@ -614,7 +705,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 	case CAM_FORMAT_MIPI_RAW_12:
@@ -630,7 +721,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 	case CAM_FORMAT_MIPI_RAW_14:
@@ -646,7 +737,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 	case CAM_FORMAT_PLAIN16_10:
@@ -666,7 +757,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 
@@ -684,7 +775,7 @@ static int cam_tfe_bus_acquire_rdi_wm(
 			rsrc_data->height = 0;
 			rsrc_data->stride =
 				CAM_TFE_RDI_BUS_DEFAULT_STRIDE;
-			rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+			rsrc_data->en_cfg = (0x1 << en_cfg_shift) | 0x1;
 		}
 		break;
 	default:
@@ -711,14 +802,16 @@ static int cam_tfe_bus_acquire_wm(
 	struct cam_tfe_bus_wm_resource_data  *rsrc_data = NULL;
 	uint32_t wm_idx = 0;
 	int rc = 0;
-
 	*wm_res = NULL;
 	/* No need to allocate for BUS TFE OUT to WM is fixed. */
-	wm_idx = cam_tfe_bus_get_wm_idx(tfe_out_res_id, plane,
-		bus_priv->common_data.pdaf_rdi2_mux_en);
+	if (bus_priv->common_data.is_lite)
+		wm_idx = cam_tfe_lite_bus_get_wm_idx(tfe_out_res_id, plane);
+	else
+		wm_idx = cam_tfe_bus_get_wm_idx(tfe_out_res_id, plane,
+			bus_priv->common_data.pdaf_rdi2_mux_en);
 	if (wm_idx < 0 || wm_idx >= bus_priv->num_client) {
-		CAM_ERR(CAM_ISP, "Unsupported TFE out %d plane %d",
-			tfe_out_res_id, plane);
+		CAM_ERR(CAM_ISP, "Unsupported TFE out %d plane %d wm id %d num client %d",
+			tfe_out_res_id, plane, wm_idx, bus_priv->num_client);
 		return -EINVAL;
 	}
 
@@ -754,8 +847,8 @@ static int cam_tfe_bus_acquire_wm(
 	/* Set WM offset value to default */
 	rsrc_data->offset  = 0;
 
-	if (((rsrc_data->index >= 7) && (rsrc_data->index <= 9)) &&
-		(tfe_out_res_id != CAM_TFE_BUS_TFE_OUT_PDAF)) {
+	if (bus_priv->common_data.is_lite || (((rsrc_data->index >= 7) &&
+		(rsrc_data->index <= 9)) && (tfe_out_res_id != CAM_TFE_BUS_TFE_OUT_PDAF))) {
 		/* WM 7-9 refers to RDI 0/ RDI 1/RDI 2 */
 		rc = cam_tfe_bus_acquire_rdi_wm(rsrc_data);
 		if (rc)
@@ -818,11 +911,53 @@ static int cam_tfe_bus_acquire_wm(
 		rsrc_data->width = 0;
 		rsrc_data->height = 0;
 		rsrc_data->stride = 1;
-		rsrc_data->en_cfg = (0x1 << 16) | 0x1;
+		rsrc_data->en_cfg = (0x1 << rsrc_data->common_data->en_cfg_shift) | 0x1;
 
 		/*RS state packet format*/
 		if (rsrc_data->index == 15)
 			rsrc_data->pack_fmt = 0x9;
+	} else if (rsrc_data->index == 16) {
+		/* LCR */
+		switch (rsrc_data->format) {
+		case CAM_FORMAT_PLAIN16_16:
+			rsrc_data->stride = ALIGNUP(rsrc_data->width * 2, 8);
+			rsrc_data->en_cfg = 0x1;
+			/* LSB aligned */
+			rsrc_data->pack_fmt |= (1 <<
+				bus_priv->common_data.pack_align_shift);
+			break;
+		default:
+			CAM_ERR(CAM_ISP, "Invalid format %d out_type:%d index: %d",
+				rsrc_data->format, tfe_out_res_id, rsrc_data->index);
+			return -EINVAL;
+		}
+	} else if (rsrc_data->index == 17) {
+		/* PD_PREPROCESSED */
+		switch (rsrc_data->format) {
+		case CAM_FORMAT_PLAIN16_16:
+			rsrc_data->stride = ALIGNUP(rsrc_data->width * 2, 8);
+			rsrc_data->en_cfg = 0x1;
+			break;
+		default:
+			CAM_ERR(CAM_ISP, "Invalid format %d out_type:%d index: %d",
+				rsrc_data->format, tfe_out_res_id, rsrc_data->index);
+			return -EINVAL;
+		}
+	} else if (rsrc_data->index == 18) {
+		/* PD PARSED */
+		switch (rsrc_data->format) {
+		case CAM_FORMAT_PLAIN16_16:
+			rsrc_data->stride = ALIGNUP(rsrc_data->width * 2, 8);
+			rsrc_data->en_cfg = 0x1;
+			/* LSB aligned */
+			rsrc_data->pack_fmt |= (1 <<
+				bus_priv->common_data.pack_align_shift);
+			break;
+		default:
+			CAM_ERR(CAM_ISP, "Invalid format %d out_type:%d index: %d",
+				rsrc_data->format, tfe_out_res_id, rsrc_data->index);
+			return -EINVAL;
+		}
 	} else {
 		CAM_ERR(CAM_ISP, "Invalid WM:%d requested", rsrc_data->index);
 		return -EINVAL;
@@ -875,13 +1010,15 @@ static int cam_tfe_bus_start_wm(struct cam_isp_resource_node *wm_res)
 		wm_res->res_priv;
 	struct cam_tfe_bus_common_data        *common_data =
 		rsrc_data->common_data;
+	int height_shift = rsrc_data->common_data->height_shift;
 
 	/* Skip to overwrite if wm bandwidth limiter blob already sent */
 	if (!rsrc_data->limiter_blob_status)
 		cam_io_w(rsrc_data->common_data->counter_limit_mask,
 			common_data->mem_base + rsrc_data->hw_regs->bw_limit);
 
-	cam_io_w((rsrc_data->height << 16) | rsrc_data->width,
+	cam_io_w(0xf, common_data->mem_base + rsrc_data->hw_regs->bw_limit);
+	cam_io_w((rsrc_data->height << height_shift) | rsrc_data->width,
 		common_data->mem_base + rsrc_data->hw_regs->image_cfg_0);
 	cam_io_w(rsrc_data->pack_fmt,
 		common_data->mem_base + rsrc_data->hw_regs->packer_cfg);
@@ -1745,6 +1882,8 @@ static const char *cam_tfe_bus_rup_type(
 		return "RDI1 RUP";
 	case CAM_ISP_HW_TFE_IN_RDI2:
 		return "RDI2 RUP";
+	case CAM_ISP_HW_TFE_IN_PDLIB:
+		return "PDLIB RUP";
 	default:
 		return "invalid rup group";
 	}
@@ -2074,7 +2213,8 @@ static int cam_tfe_bus_update_wm(void *priv, void *cmd_args,
 
 		wm_data = tfe_out_data->wm_res[i]->res_priv;
 		/* update width register */
-		val = ((wm_data->height << 16) | (wm_data->width & 0xFFFF));
+		val = ((wm_data->height << wm_data->common_data->height_shift) |
+			(wm_data->width & 0xFFFF));
 		CAM_TFE_ADD_REG_VAL_PAIR(reg_val_pair, j,
 			wm_data->hw_regs->image_cfg_0, val);
 		CAM_DBG(CAM_ISP, "WM:%d image height and width 0x%x",
@@ -2684,6 +2824,9 @@ int cam_tfe_bus_init(
 	bus_priv->common_data.max_bw_counter_limit = hw_info->max_bw_counter_limit;
 	bus_priv->common_data.counter_limit_shift = hw_info->counter_limit_shift;
 	bus_priv->common_data.counter_limit_mask = hw_info->counter_limit_mask;
+	bus_priv->common_data.en_cfg_shift = hw_info->en_cfg_shift;
+	bus_priv->common_data.height_shift = hw_info->height_shift;
+	bus_priv->common_data.pack_align_shift = hw_info->pack_align_shift;
 
 	for (i = 0; i < CAM_TFE_BUS_IRQ_REGISTERS_MAX; i++)
 		bus_priv->bus_irq_error_mask[i] =

+ 12 - 1
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_bus.h

@@ -12,7 +12,7 @@
 #include "cam_isp_hw.h"
 #include "cam_tfe_hw_intf.h"
 
-#define CAM_TFE_BUS_MAX_CLIENTS            16
+#define CAM_TFE_BUS_MAX_CLIENTS            19
 #define CAM_TFE_BUS_MAX_SUB_GRPS            4
 #define CAM_TFE_BUS_MAX_PERF_CNT_REG        8
 #define CAM_TFE_BUS_MAX_IRQ_REGISTERS       2
@@ -61,6 +61,7 @@ enum cam_tfe_bus_comp_grp_id {
 	CAM_TFE_BUS_COMP_GRP_8,
 	CAM_TFE_BUS_COMP_GRP_9,
 	CAM_TFE_BUS_COMP_GRP_10,
+	CAM_TFE_BUS_COMP_GRP_11,
 	CAM_TFE_BUS_COMP_GRP_MAX,
 };
 
@@ -69,6 +70,7 @@ enum cam_tfe_bus_rup_grp_id {
 	CAM_TFE_BUS_RUP_GRP_1,
 	CAM_TFE_BUS_RUP_GRP_2,
 	CAM_TFE_BUS_RUP_GRP_3,
+	CAM_TFE_BUS_RUP_GRP_4,
 	CAM_TFE_BUS_RUP_GRP_MAX,
 };
 
@@ -88,6 +90,9 @@ enum cam_tfe_bus_tfe_out_id {
 	CAM_TFE_BUS_TFE_OUT_DS4,
 	CAM_TFE_BUS_TFE_OUT_DS16,
 	CAM_TFE_BUS_TFE_OUT_AI,
+	CAM_TFE_BUS_TFE_OUT_PD_LCR_STATS,
+	CAM_TFE_BUS_TFE_OUT_PD_PREPROCESSED,
+	CAM_TFE_BUS_TFE_OUT_PD_PARSED,
 	CAM_TFE_BUS_TFE_OUT_MAX,
 };
 
@@ -145,6 +150,7 @@ struct cam_tfe_bus_reg_offset_bus_client {
 	uint32_t irq_subsample_pattern;
 	uint32_t framedrop_period;
 	uint32_t framedrop_pattern;
+	uint32_t system_cache_cfg;
 	uint32_t addr_status_0;
 	uint32_t addr_status_1;
 	uint32_t addr_status_2;
@@ -199,6 +205,8 @@ struct cam_tfe_bus_tfe_out_hw_info {
  * @max_bw_counter_limit:  Max BW counter limit
  * @counter_limit_shift:   Mask shift for BW counter limit
  * @counter_limit_mask:    Default Mask of BW limit counter
+ * @en_cfg_shift:          bus client frame based enable bit
+ * @pack_align_shift:      pack alignment shift
  */
 struct cam_tfe_bus_hw_info {
 	struct cam_tfe_bus_reg_offset_common common_reg;
@@ -211,6 +219,8 @@ struct cam_tfe_bus_hw_info {
 	uint32_t num_comp_grp;
 	uint32_t max_wm_per_comp_grp;
 	uint32_t comp_done_shift;
+	uint32_t en_cfg_shift;
+	uint32_t height_shift;
 	uint32_t top_bus_wr_irq_shift;
 	uint32_t comp_buf_done_mask;
 	uint32_t comp_rup_done_mask;
@@ -221,6 +231,7 @@ struct cam_tfe_bus_hw_info {
 	uint32_t max_bw_counter_limit;
 	uint32_t counter_limit_shift;
 	uint32_t counter_limit_mask;
+	uint32_t pack_align_shift;
 };
 
 /*

+ 422 - 69
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_core.c

@@ -30,6 +30,7 @@ static const char drv_name[] = "tfe";
 #define CAM_TFE_DELAY_BW_REDUCTION_NUM_FRAMES 3
 #define CAM_TFE_CAMIF_IRQ_SOF_DEBUG_CNT_MAX  2
 #define CAM_TFE_DELAY_BW_REDUCTION_NUM_FRAMES 3
+#define CAM_TFE_MAX_OUT_OF_SYNC_ERR_COUNT     3
 
 struct cam_tfe_top_common_data {
 	struct cam_hw_soc_info                     *soc_info;
@@ -58,6 +59,8 @@ struct cam_tfe_top_priv {
 	struct timespec64                    eof_ts;
 	struct timespec64                    error_ts;
 	uint32_t                             top_debug;
+	uint32_t                             last_mup_val;
+	atomic_t                             switch_out_of_sync_cnt;
 };
 
 struct cam_tfe_camif_data {
@@ -108,6 +111,23 @@ struct cam_tfe_rdi_data {
 	uint32_t                                     last_line;
 };
 
+struct cam_tfe_ppp_data {
+	void __iomem                                *mem_base;
+	struct cam_hw_intf                          *hw_intf;
+	struct cam_tfe_top_reg_offset_common        *common_reg;
+	struct cam_tfe_ppp_reg                      *ppp_reg;
+	struct cam_tfe_ppp_reg_data                 *reg_data;
+	cam_hw_mgr_event_cb_func                     event_cb;
+	void                                        *priv;
+	enum cam_isp_hw_sync_mode                    sync_mode;
+	uint32_t                                     pix_pattern;
+	uint32_t                                     left_first_pixel;
+	uint32_t                                     left_last_pixel;
+	uint32_t                                     first_line;
+	uint32_t                                     last_line;
+	bool                                         lcr_enable;
+};
+
 static int cam_tfe_validate_pix_pattern(uint32_t pattern)
 {
 	int rc;
@@ -238,9 +258,12 @@ static void cam_tfe_log_tfe_in_debug_status(
 	void __iomem                         *mem_base;
 	struct cam_tfe_camif_data            *camif_data;
 	struct cam_tfe_rdi_data              *rdi_data;
+	struct cam_tfe_top_reg_offset_common *common_reg;
+	struct cam_tfe_ppp_data              *ppp_data;
 	uint32_t  i, val_0, val_1;
 
 	mem_base = top_priv->common_data.soc_info->reg_map[0].mem_base;
+	common_reg = top_priv->common_data.common_reg;
 
 	for (i = 0; i < CAM_TFE_TOP_IN_PORT_MAX; i++) {
 		if ((top_priv->in_rsrc[i].res_state !=
@@ -257,7 +280,7 @@ static void cam_tfe_log_tfe_in_debug_status(
 			CAM_INFO(CAM_ISP,
 				"camif debug1:0x%x Height:0x%x, width:0x%x",
 				val_1,
-				((val_0 >> 16) & 0x1FFF),
+				((val_0 >> common_reg->height_shift) & 0x1FFF),
 				(val_0 & 0x1FFF));
 			CAM_INFO(CAM_ISP,
 				"Acquired sync mode:%d left start pxl:0x%x end_pixel:0x%x",
@@ -280,6 +303,28 @@ static void cam_tfe_log_tfe_in_debug_status(
 				camif_data->vbi_value,
 				camif_data->hbi_value);
 
+		} else if (top_priv->in_rsrc[i].res_id == CAM_ISP_HW_TFE_IN_PDLIB) {
+			ppp_data = (struct cam_tfe_ppp_data  *)
+				top_priv->in_rsrc[i].res_priv;
+			val_0 = cam_io_r(mem_base  +
+				ppp_data->ppp_reg->ppp_debug_0);
+			val_1 = cam_io_r(mem_base  +
+				ppp_data->ppp_reg->ppp_debug_1);
+			CAM_INFO(CAM_ISP,
+				"PDLIB res id:%d debug1:0x%x Height:0x%x, width:0x%x",
+				top_priv->in_rsrc[i].res_id,
+				val_1, ((val_0 >> 16) & 0x1FFF),
+				(val_0 & 0x1FFF));
+			CAM_INFO(CAM_ISP,
+				"sync mode:%d left start pxl:0x%x end_pixel:0x%x",
+				ppp_data->sync_mode,
+				ppp_data->left_first_pixel,
+				ppp_data->left_last_pixel);
+			CAM_INFO(CAM_ISP,
+				"sync mode:%d line start:0x%x line end:0x%x",
+				ppp_data->sync_mode,
+				ppp_data->first_line,
+				ppp_data->last_line);
 		} else if ((top_priv->in_rsrc[i].res_id >=
 			CAM_ISP_HW_TFE_IN_RDI0) ||
 			(top_priv->in_rsrc[i].res_id <=
@@ -293,7 +338,7 @@ static void cam_tfe_log_tfe_in_debug_status(
 			CAM_INFO(CAM_ISP,
 				"RDI res id:%d debug1:0x%x Height:0x%x, width:0x%x",
 				top_priv->in_rsrc[i].res_id,
-				val_1, ((val_0 >> 16) & 0x1FFF),
+				val_1, ((val_0 >> common_reg->height_shift) & 0x1FFF),
 				(val_0 & 0x1FFF));
 			CAM_INFO(CAM_ISP,
 				"sync mode:%d left start pxl:0x%x end_pixel:0x%x",
@@ -311,7 +356,9 @@ static void cam_tfe_log_tfe_in_debug_status(
 static void cam_tfe_log_error_irq_status(
 	struct cam_tfe_hw_core_info          *core_info,
 	struct cam_tfe_top_priv              *top_priv,
-	struct cam_tfe_irq_evt_payload       *evt_payload)
+	struct cam_tfe_irq_evt_payload       *evt_payload,
+	struct cam_isp_hw_error_event_info   *err_evt_info,
+	int8_t                               *report_err)
 {
 	struct cam_tfe_hw_info               *hw_info;
 	void __iomem                         *mem_base;
@@ -319,15 +366,17 @@ static void cam_tfe_log_error_irq_status(
 	struct cam_tfe_soc_private           *soc_private;
 
 	struct cam_tfe_clc_hw_status         *clc_hw_status;
+	struct cam_tfe_top_reg_offset_common *common_reg;
 	struct timespec64 ts;
 	uint32_t  i, val_0, val_1, val_2, val_3;
 
-
+	*report_err = 1;
 	ktime_get_boottime_ts64(&ts);
 	hw_info = core_info->tfe_hw_info;
 	mem_base = top_priv->common_data.soc_info->reg_map[0].mem_base;
 	soc_info = top_priv->common_data.soc_info;
 	soc_private = top_priv->common_data.soc_info->soc_private;
+	common_reg = top_priv->common_data.common_reg;
 
 	CAM_INFO(CAM_ISP, "current monotonic timestamp:[%lld.%06lld]",
 		ts.tv_sec, ts.tv_nsec/1000);
@@ -346,26 +395,22 @@ static void cam_tfe_log_error_irq_status(
 		evt_payload->irq_reg_val[0], evt_payload->irq_reg_val[1],
 		evt_payload->irq_reg_val[2]);
 
-	for (i = 0; i < top_priv->common_data.common_reg->num_debug_reg; i++) {
+	for (i = 0; i < common_reg->num_debug_reg; i++) {
 		val_0 = cam_io_r(mem_base  +
-			top_priv->common_data.common_reg->debug_reg[i]);
-		CAM_INFO(CAM_ISP, "Top debug [%d]:0x%x", i, val_0);
+			common_reg->debug_reg[i]);
+		CAM_INFO(CAM_ISP, "Top debug [i]:0x%x", i, val_0);
 	}
 
 	cam_cpas_dump_camnoc_buff_fill_info(soc_private->cpas_handle);
 
-	for (i = 0; i < top_priv->common_data.common_reg->num_perf_cfg; i++) {
-		val_0 = cam_io_r(mem_base  +
-			top_priv->common_data.common_reg->perf_cfg[i].perf_pixel_count);
+	for (i = 0; i < common_reg->num_perf_cfg; i++) {
+		val_0 = cam_io_r(mem_base + common_reg->perf_cfg[i].perf_pixel_count);
 
-		val_1 = cam_io_r(mem_base  +
-			top_priv->common_data.common_reg->perf_cfg[i].perf_line_count);
+		val_1 = cam_io_r(mem_base + common_reg->perf_cfg[i].perf_line_count);
 
-		val_2 = cam_io_r(mem_base  +
-			top_priv->common_data.common_reg->perf_cfg[i].perf_stall_count);
+		val_2 = cam_io_r(mem_base + common_reg->perf_cfg[i].perf_stall_count);
 
-		val_3 = cam_io_r(mem_base  +
-			top_priv->common_data.common_reg->perf_cfg[i].perf_always_count);
+		val_3 = cam_io_r(mem_base + common_reg->perf_cfg[i].perf_always_count);
 
 		CAM_INFO(CAM_ISP,
 			"Top perf cnt [%d] pix:0x%x line:0x%x stall:0x%x always:0x%x",
@@ -388,54 +433,87 @@ static void cam_tfe_log_error_irq_status(
 
 	/* Check the overflow errors */
 	if (evt_payload->irq_reg_val[0] & hw_info->error_irq_mask[0]) {
-		if (evt_payload->irq_reg_val[0] & BIT(8))
-			CAM_INFO(CAM_ISP, "PP_FRAME_DROP");
+		if (evt_payload->irq_reg_val[0] & common_reg->pp_frame_drop_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PP_FRAME_DROP", core_info->core_index);
+
+		if (evt_payload->irq_reg_val[0] & common_reg->rdi0_frame_drop_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI0_FRAME_DROP", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(9))
-			CAM_INFO(CAM_ISP, "RDI0_FRAME_DROP");
+		if (evt_payload->irq_reg_val[0] & common_reg->rdi1_frame_drop_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI1_FRAME_DROP", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(10))
-			CAM_INFO(CAM_ISP, "RDI1_FRAME_DROP");
+		if (evt_payload->irq_reg_val[0] & common_reg->rdi2_frame_drop_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI2_FRAME_DROP", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(11))
-			CAM_INFO(CAM_ISP, "RDI2_FRAME_DROP");
+		if (evt_payload->irq_reg_val[0] & common_reg->ppp_frame_drop_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PDAF_FRAME_DROP", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(16))
-			CAM_INFO(CAM_ISP, "PP_OVERFLOW");
+		if (evt_payload->irq_reg_val[0] & common_reg->pp_overflow_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PP_OVERFLOW", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(17))
-			CAM_INFO(CAM_ISP, "RDI0_OVERFLOW");
+		if (evt_payload->irq_reg_val[0] & common_reg->rdi0_overflow_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI0_OVERFLOW", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(18))
-			CAM_INFO(CAM_ISP, "RDI1_OVERFLOW");
+		if (evt_payload->irq_reg_val[0] & common_reg->rdi1_overflow_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI1_OVERFLOW", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[0] & BIT(19))
-			CAM_INFO(CAM_ISP, "RDI2_OVERFLOW");
+		if (evt_payload->irq_reg_val[0] & common_reg->rdi2_overflow_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI2_OVERFLOW", core_info->core_index);
+
+		if (evt_payload->irq_reg_val[0] & common_reg->ppp_overflow_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PDAF_OVERFLOW", core_info->core_index);
+
+		if (evt_payload->irq_reg_val[0] & common_reg->out_of_sync_frame_drop_bit) {
+			CAM_INFO(CAM_ISP,
+				"TFE %d SENSOR_SWITCH_OUT_OF_SYNC_FRAME_DROP mup: last %d curr %d",
+				core_info->core_index, top_priv->last_mup_val,
+				((cam_io_r(mem_base + common_reg->reg_update_cmd) >>
+				common_reg->mup_shift_val) & 1));
+			*report_err = 0;
+			atomic_inc(&top_priv->switch_out_of_sync_cnt);
+			if (atomic_read(&top_priv->switch_out_of_sync_cnt) >=
+				CAM_TFE_MAX_OUT_OF_SYNC_ERR_COUNT) {
+				*report_err = 1;
+				err_evt_info->err_type = CAM_TFE_IRQ_STATUS_OUT_OF_SYNC;
+				CAM_ERR(CAM_ISP, "TFE %d out of sync frame count: %d",
+					core_info->core_index, top_priv->switch_out_of_sync_cnt);
+			}
+		}
 	}
 
 	/* Check the violation errors */
 	if (evt_payload->irq_reg_val[2] & hw_info->error_irq_mask[2]) {
-		if (evt_payload->irq_reg_val[2] & BIT(0))
-			CAM_INFO(CAM_ISP, "PP_CAMIF_VIOLATION");
+		if (evt_payload->irq_reg_val[2] & common_reg->pp_camif_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PP_CAMIF_VIOLATION", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[2] & BIT(1))
-			CAM_INFO(CAM_ISP, "PP_VIOLATION");
+		if (evt_payload->irq_reg_val[2] & common_reg->pp_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PP_VIOLATION", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[2] & BIT(2))
-			CAM_INFO(CAM_ISP, "RDI0_CAMIF_VIOLATION");
+		if (evt_payload->irq_reg_val[2] & common_reg->rdi0_camif_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI0_CAMIF_VIOLATION", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[2] & BIT(3))
-			CAM_INFO(CAM_ISP, "RDI1_CAMIF_VIOLATION");
+		if (evt_payload->irq_reg_val[2] & common_reg->rdi1_camif_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI1_CAMIF_VIOLATION", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[2] & BIT(4))
-			CAM_INFO(CAM_ISP, "RDI2_CAMIF_VIOLATION");
+		if (evt_payload->irq_reg_val[2] & common_reg->rdi2_camif_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d RDI2_CAMIF_VIOLATION", core_info->core_index);
 
-		if (evt_payload->irq_reg_val[2] & BIT(5))
-			CAM_INFO(CAM_ISP, "DIAG_VIOLATION");
+		if (evt_payload->irq_reg_val[2] & common_reg->diag_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d DIAG_VIOLATION", core_info->core_index);
 
-		val_0 = cam_io_r(mem_base  +
-		top_priv->common_data.common_reg->violation_status);
-		CAM_INFO(CAM_ISP, "TOP Violation status:0x%x", val_0);
+		if (evt_payload->irq_reg_val[2] & common_reg->ppp_camif_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PDAF_CAMIF_VIOLATION", core_info->core_index);
+
+		if (evt_payload->irq_reg_val[2] & common_reg->ppp_violation_bit)
+			CAM_INFO(CAM_ISP, "TFE %d PDAF_VIOLATION", core_info->core_index);
+
+		if (evt_payload->irq_reg_val[2] & common_reg->dyamanic_switch_violation_bit)
+			CAM_INFO(CAM_ISP,
+				"TFE %d DYNAMIC_SHDR_MODE_SWITCH_VIOLATION mup val %d",
+				core_info->core_index, top_priv->last_mup_val);
+
+		val_0 = cam_io_r(mem_base + common_reg->violation_status);
+		CAM_INFO(CAM_ISP, "TFE %d TOP Violation status:0x%x", core_info->core_index, val_0);
 	}
 
 	core_info->tfe_bus->bottom_half_handler(
@@ -460,6 +538,7 @@ static int cam_tfe_error_irq_bottom_half(
 	struct cam_isp_hw_event_info         evt_info;
 	struct cam_tfe_hw_info              *hw_info;
 	uint32_t   error_detected = 0;
+	int8_t report_err = 1;
 
 	hw_info = core_info->tfe_hw_info;
 	evt_info.hw_idx = core_info->core_index;
@@ -483,13 +562,16 @@ static int cam_tfe_error_irq_bottom_half(
 		top_priv->error_ts.tv_nsec =
 			evt_payload->ts.mono_time.tv_nsec;
 
-		cam_tfe_log_error_irq_status(core_info, top_priv, evt_payload);
-		if (event_cb)
-			event_cb(event_cb_priv,
-				CAM_ISP_HW_EVENT_ERROR, (void *)&evt_info);
-		else
-			CAM_ERR(CAM_ISP, "TFE:%d invalid eventcb:",
-				core_info->core_index);
+		cam_tfe_log_error_irq_status(core_info, top_priv,
+			evt_payload, &err_evt_info, &report_err);
+		if (report_err) {
+			if (event_cb)
+				event_cb(event_cb_priv, CAM_ISP_HW_EVENT_ERROR,
+					(void *)&evt_info);
+			else
+				CAM_ERR(CAM_ISP, "TFE:%d invalid eventcb:",
+					core_info->core_index);
+		}
 	}
 
 	return 0;
@@ -539,6 +621,8 @@ static int cam_tfe_rdi_irq_bottom_half(
 			rdi_priv->event_cb(rdi_priv->priv,
 				CAM_ISP_HW_EVENT_SOF, (void *)&evt_info);
 
+		atomic_set(&top_priv->switch_out_of_sync_cnt, 0);
+
 		if (top_priv->top_debug &
 			CAMIF_DEBUG_ENABLE_SENSOR_DIAG_STATUS) {
 			common_reg  = rdi_priv->common_reg;
@@ -573,6 +657,84 @@ static int cam_tfe_rdi_irq_bottom_half(
 	return 0;
 }
 
+static int cam_tfe_ppp_irq_bottom_half(
+	struct cam_tfe_top_priv              *top_priv,
+	struct cam_isp_resource_node         *ppp_node,
+	bool                                  epoch_process,
+	struct cam_tfe_irq_evt_payload       *evt_payload)
+{
+	struct cam_tfe_ppp_data               *ppp_priv;
+	struct cam_isp_hw_event_info           evt_info;
+	struct cam_hw_info                    *hw_info;
+	struct cam_tfe_top_reg_offset_common  *common_reg;
+	uint32_t                               val, val2;
+
+	ppp_priv = (struct cam_tfe_ppp_data    *)ppp_node->res_priv;
+	hw_info = ppp_node->hw_intf->hw_priv;
+
+	evt_info.hw_idx   = ppp_node->hw_intf->hw_idx;
+	evt_info.res_id   = ppp_node->res_id;
+	evt_info.res_type = ppp_node->res_type;
+
+	if ((!epoch_process) && (evt_payload->irq_reg_val[1] &
+		ppp_priv->reg_data->eof_irq_mask)) {
+		CAM_DBG(CAM_ISP, "Received EOF");
+		top_priv->eof_ts.tv_sec =
+			evt_payload->ts.mono_time.tv_sec;
+		top_priv->eof_ts.tv_nsec =
+			evt_payload->ts.mono_time.tv_nsec;
+
+		if (ppp_priv->event_cb)
+			ppp_priv->event_cb(ppp_priv->priv,
+				CAM_ISP_HW_EVENT_EOF, (void *)&evt_info);
+	}
+
+	if ((!epoch_process) && (evt_payload->irq_reg_val[1] &
+		ppp_priv->reg_data->sof_irq_mask)) {
+		CAM_DBG(CAM_ISP, "Received SOF");
+		top_priv->sof_ts.tv_sec =
+			evt_payload->ts.mono_time.tv_sec;
+		top_priv->sof_ts.tv_nsec =
+			evt_payload->ts.mono_time.tv_nsec;
+
+		if (ppp_priv->event_cb)
+			ppp_priv->event_cb(ppp_priv->priv,
+				CAM_ISP_HW_EVENT_SOF, (void *)&evt_info);
+
+		if (top_priv->top_debug &
+			CAMIF_DEBUG_ENABLE_SENSOR_DIAG_STATUS) {
+			common_reg  = ppp_priv->common_reg;
+			val = cam_io_r(ppp_priv->mem_base +
+				common_reg->diag_sensor_status_0);
+			val2 =  cam_io_r(ppp_priv->mem_base +
+				common_reg->diag_sensor_status_1);
+			CAM_INFO(CAM_ISP,
+				"TFE:%d diag sensor hbi min error:%d neq hbi:%d HBI:%d VBI:%d",
+				ppp_node->hw_intf->hw_idx,
+				((val >> common_reg->diag_min_hbi_error_shift)
+					& 0x1),
+				((val >> common_reg->diag_neq_hbi_shift) & 0x1),
+				(val & common_reg->diag_sensor_hbi_mask),
+				val2);
+		}
+	}
+
+	if (epoch_process && (evt_payload->irq_reg_val[1] &
+		ppp_priv->reg_data->epoch0_irq_mask)) {
+		CAM_DBG(CAM_ISP, "Received EPOCH0");
+		top_priv->epoch_ts.tv_sec =
+			evt_payload->ts.mono_time.tv_sec;
+		top_priv->epoch_ts.tv_nsec =
+			evt_payload->ts.mono_time.tv_nsec;
+
+		if (ppp_priv->event_cb)
+			ppp_priv->event_cb(ppp_priv->priv,
+				CAM_ISP_HW_EVENT_EPOCH, (void *)&evt_info);
+	}
+
+	return 0;
+}
+
 static int cam_tfe_camif_irq_bottom_half(
 	struct cam_tfe_top_priv              *top_priv,
 	struct cam_isp_resource_node         *camif_node,
@@ -631,6 +793,8 @@ static int cam_tfe_camif_irq_bottom_half(
 			camif_priv->event_cb(camif_priv->priv,
 				CAM_ISP_HW_EVENT_SOF, (void *)&evt_info);
 
+		atomic_set(&top_priv->switch_out_of_sync_cnt, 0);
+
 		if (top_priv->top_debug &
 			CAMIF_DEBUG_ENABLE_SENSOR_DIAG_STATUS) {
 			common_reg  = camif_priv->common_reg;
@@ -674,6 +838,7 @@ static int cam_tfe_irq_bottom_half(void *handler_priv,
 	struct cam_tfe_irq_evt_payload      *evt_payload;
 	struct cam_tfe_camif_data           *camif_priv;
 	struct cam_tfe_rdi_data             *rdi_priv;
+	struct cam_tfe_ppp_data             *ppp_priv;
 	cam_hw_mgr_event_cb_func             event_cb = NULL;
 	void                                *event_cb_priv = NULL;
 	uint32_t i;
@@ -706,6 +871,20 @@ static int cam_tfe_irq_bottom_half(void *handler_priv,
 					&top_priv->in_rsrc[i], false,
 					evt_payload);
 
+		} else if ((top_priv->in_rsrc[i].res_id ==
+			CAM_ISP_HW_TFE_IN_PDLIB) &&
+			(top_priv->in_rsrc[i].res_state ==
+			CAM_ISP_RESOURCE_STATE_STREAMING)) {
+			ppp_priv = (struct cam_tfe_ppp_data *)
+				top_priv->in_rsrc[i].res_priv;
+			event_cb = ppp_priv->event_cb;
+			event_cb_priv = ppp_priv->priv;
+
+			if (ppp_priv->reg_data->subscribe_irq_mask[1] &
+				evt_payload->irq_reg_val[1])
+				cam_tfe_ppp_irq_bottom_half(top_priv,
+					&top_priv->in_rsrc[i], false,
+					evt_payload);
 		} else if ((top_priv->in_rsrc[i].res_id >=
 			CAM_ISP_HW_TFE_IN_RDI0) &&
 			(top_priv->in_rsrc[i].res_id <=
@@ -750,6 +929,17 @@ static int cam_tfe_irq_bottom_half(void *handler_priv,
 				cam_tfe_camif_irq_bottom_half(top_priv,
 					&top_priv->in_rsrc[i], true,
 					evt_payload);
+		} else if ((top_priv->in_rsrc[i].res_id ==
+			CAM_ISP_HW_TFE_IN_PDLIB) &&
+			(top_priv->in_rsrc[i].res_state ==
+			CAM_ISP_RESOURCE_STATE_STREAMING)) {
+			ppp_priv = (struct cam_tfe_ppp_data *)
+				top_priv->in_rsrc[i].res_priv;
+			if (ppp_priv->reg_data->subscribe_irq_mask[1] &
+				evt_payload->irq_reg_val[1])
+				cam_tfe_ppp_irq_bottom_half(top_priv,
+					&top_priv->in_rsrc[i], true,
+					evt_payload);
 		} else if ((top_priv->in_rsrc[i].res_id >=
 			CAM_ISP_HW_TFE_IN_RDI0) &&
 			(top_priv->in_rsrc[i].res_id <=
@@ -1256,24 +1446,46 @@ static int cam_tfe_top_get_base(struct cam_tfe_top_priv *top_priv,
 	return 0;
 }
 
+static int cam_tfe_top_update_mup(
+	struct cam_tfe_top_priv *top_priv,
+	struct cam_isp_mode_switch_data *mup_config)
+{
+	uint32_t mup_val = 0, final_mup = 0;
+	struct cam_tfe_top_reg_offset_common *common_reg;
+
+	mup_val = mup_config->mup;
+	common_reg = top_priv->common_data.common_reg;
+
+	if (mup_config->mup_en) {
+		final_mup = (mup_val << common_reg->mup_shift_val);
+		top_priv->last_mup_val = mup_val;
+	} else {
+		final_mup = (top_priv->last_mup_val << common_reg->mup_shift_val);
+	}
+
+	return final_mup;
+}
+
 static int cam_tfe_top_get_reg_update(
 	struct cam_tfe_top_priv *top_priv,
 	void *cmd_args, uint32_t arg_size)
 {
-	uint32_t                          size = 0;
-	uint32_t                          reg_val_pair[2];
-	struct cam_isp_hw_get_cmd_update *cdm_args = cmd_args;
-	struct cam_cdm_utils_ops         *cdm_util_ops = NULL;
-	struct cam_tfe_camif_data        *camif_rsrc_data = NULL;
-	struct cam_tfe_rdi_data          *rdi_rsrc_data = NULL;
-	struct cam_isp_resource_node     *in_res;
+	uint32_t                             size = 0;
+	uint32_t                             reg_val_pair[2];
+	struct cam_isp_hw_get_cmd_update     *cdm_args = cmd_args;
+	struct cam_cdm_utils_ops             *cdm_util_ops = NULL;
+	struct cam_tfe_camif_data            *camif_rsrc_data = NULL;
+	struct cam_tfe_rdi_data              *rdi_rsrc_data = NULL;
+	struct cam_isp_resource_node         *in_res;
+	struct cam_isp_mode_switch_data      *mup_config = NULL;
+	struct cam_tfe_top_reg_offset_common *common_reg;
 
 	if (arg_size != sizeof(struct cam_isp_hw_get_cmd_update)) {
 		CAM_ERR(CAM_ISP, "Invalid cmd size");
 		return -EINVAL;
 	}
 
-	if (!cdm_args || !cdm_args->res) {
+	if (!cdm_args || !cdm_args->res || !top_priv) {
 		CAM_ERR(CAM_ISP, "Invalid args");
 		return -EINVAL;
 	}
@@ -1285,10 +1497,11 @@ static int cam_tfe_top_get_reg_update(
 		return -EINVAL;
 	}
 
+	soc_info = top_priv->common_data.soc_info;
 	in_res = cdm_args->res;
 	size = cdm_util_ops->cdm_required_size_reg_random(1);
 	/* since cdm returns dwords, we need to convert it into bytes */
-	if ((size * 4) > cdm_args->cmd.size) {
+	if ((!cdm_args->reg_write) && ((size * 4) > cdm_args->cmd.size)) {
 		CAM_ERR(CAM_ISP, "buf size:%d is not sufficient, expected: %d",
 			cdm_args->cmd.size, size);
 		return -EINVAL;
@@ -1304,12 +1517,35 @@ static int cam_tfe_top_get_reg_update(
 		rdi_rsrc_data =  in_res->res_priv;
 		reg_val_pair[0] = rdi_rsrc_data->rdi_reg->reg_update_cmd;
 		reg_val_pair[1] = rdi_rsrc_data->reg_data->reg_update_cmd_data;
+	} else if (in_res->res_id == CAM_ISP_HW_TFE_IN_PDLIB) {
+		/*REG CMD is not supported in PDLIB. PD CAMIF takes RUP from IPP CAMIF */
+		CAM_DBG(CAM_ISP, "Reg update not supported for res %d",
+			in_res->res_id);
+		return 0;
 	}
 
-	cdm_util_ops->cdm_write_regrandom(cdm_args->cmd.cmd_buf_addr,
-		1, reg_val_pair);
+	common_reg = top_priv->common_data.common_reg;
+	if (common_reg->mup_supported) {
+		if (!cdm_args->data) {
+			CAM_ERR(CAM_ISP, "invalid data (NULL), TFE: %d mup_supported :%d",
+					top_priv->common_data.hw_intf->hw_idx , cdm_args->data);
+			return -EINVAL;
+		}
+		mup_config = (struct cam_isp_mode_switch_data *) cdm_args->data;
+		reg_val_pair[1] |= cam_tfe_top_update_mup(top_priv, mup_config);
+		CAM_DBG(CAM_ISP, "MUP supported, TFE: %d final reg_up cmd: 0x%x",
+				top_priv->common_data.hw_intf->hw_idx, reg_val_pair[1]);
+	}
+
+	if (cdm_args->reg_write) {
+		cam_io_w_mb(reg_val_pair[1],
+			soc_info->reg_map[TFE_CORE_BASE_IDX].mem_base + reg_val_pair[0]);
+	} else {
+		cdm_util_ops->cdm_write_regrandom(cdm_args->cmd.cmd_buf_addr,
+			1, reg_val_pair);
 
-	cdm_args->cmd.used_bytes = size * 4;
+		cdm_args->cmd.used_bytes = size * 4;
+	}
 
 	return 0;
 }
@@ -1860,6 +2096,22 @@ int cam_tfe_set_top_debug(struct cam_tfe_hw_core_info    *core_info,
 	return 0;
 }
 
+static int cam_tfe_bus_get_path_port_map(void *top_hw_info,
+		void *cmd_args, uint32_t arg_size)
+{
+	struct cam_isp_hw_path_port_map *arg = cmd_args;
+	struct cam_tfe_top_hw_info *hw_info =
+		(struct cam_tfe_top_hw_info  *)top_hw_info;
+	int i;
+
+	for (i = 0; i < hw_info->num_path_port_map; i++) {
+		arg->entry[i][0] = hw_info->path_port_map[i][0];
+		arg->entry[i][1] = hw_info->path_port_map[i][1];
+	}
+	arg->num_entries = hw_info->num_path_port_map;
+
+	return 0;
+}
 
 int cam_tfe_top_reserve(void *device_priv,
 	void *reserve_args, uint32_t arg_size)
@@ -1868,6 +2120,7 @@ int cam_tfe_top_reserve(void *device_priv,
 	struct cam_tfe_acquire_args             *args;
 	struct cam_tfe_hw_tfe_in_acquire_args   *acquire_args;
 	struct cam_tfe_camif_data               *camif_data;
+	struct cam_tfe_ppp_data                 *ppp_data;
 	struct cam_tfe_rdi_data                 *rdi_data;
 	uint32_t i;
 	int rc = -EINVAL;
@@ -1938,6 +2191,24 @@ int cam_tfe_top_reserve(void *device_priv,
 					top_priv->in_rsrc[i].hw_intf->hw_idx,
 					camif_data->pix_pattern,
 					camif_data->dsp_mode);
+			} else if (acquire_args->res_id == CAM_ISP_HW_TFE_IN_PDLIB) {
+				ppp_data = (struct cam_tfe_ppp_data	*)
+					top_priv->in_rsrc[i].res_priv;
+				ppp_data->pix_pattern =
+					acquire_args->in_port->pix_pattern;
+				ppp_data->sync_mode = acquire_args->sync_mode;
+				ppp_data->event_cb = args->event_cb;
+				ppp_data->priv = args->priv;
+				ppp_data->left_first_pixel =
+					acquire_args->in_port->left_start;
+				ppp_data->left_last_pixel =
+					acquire_args->in_port->left_end;
+				ppp_data->first_line =
+					acquire_args->in_port->line_start;
+				ppp_data->last_line =
+					acquire_args->in_port->line_end;
+				ppp_data->lcr_enable =
+					acquire_args->lcr_enable;
 			} else {
 				rdi_data = (struct cam_tfe_rdi_data      *)
 					top_priv->in_rsrc[i].res_priv;
@@ -2015,6 +2286,7 @@ static int cam_tfe_camif_resource_start(
 	uint32_t                             camera_hw_version = 0;
 	struct cam_hw_intf                  *tfe_device;
 	bool                                 pdaf_rdi2_mux_en = false;
+	struct cam_tfe_top_reg_offset_common *common_reg;
 
 	if (!camif_res || !core_info) {
 		CAM_ERR(CAM_ISP, "Error Invalid input arguments");
@@ -2036,7 +2308,7 @@ static int cam_tfe_camif_resource_start(
 			core_info->core_index);
 		return -ENODEV;
 	}
-
+	common_reg = top_priv->common_data.common_reg;
 	/* Config tfe core*/
 	val = 0;
 	if (rsrc_data->sync_mode == CAM_ISP_HW_SYNC_SLAVE)
@@ -2105,7 +2377,7 @@ static int cam_tfe_camif_resource_start(
 
 	epoch1_irq_mask = rsrc_data->reg_data->epoch_line_cfg &
 			0xFFFF;
-	computed_epoch_line_cfg = (epoch0_irq_mask << 16) |
+	computed_epoch_line_cfg = (epoch0_irq_mask << common_reg->epoch_shift_val) |
 			epoch1_irq_mask;
 	cam_io_w_mb(computed_epoch_line_cfg,
 			rsrc_data->mem_base +
@@ -2163,6 +2435,45 @@ static int cam_tfe_camif_resource_start(
 	return 0;
 }
 
+static int cam_tfe_ppp_resource_start(
+	struct cam_tfe_hw_core_info         *core_info,
+	struct cam_isp_resource_node        *ppp_res)
+{
+	struct cam_tfe_ppp_data             *rsrc_data;
+	uint32_t                             val = 0;
+
+	if (!ppp_res || !core_info) {
+		CAM_ERR(CAM_ISP, "Error Invalid input arguments");
+		return -EINVAL;
+	}
+
+	if (ppp_res->res_state != CAM_ISP_RESOURCE_STATE_RESERVED) {
+		CAM_ERR(CAM_ISP, "TFE:%d Error Invalid camif res res_state:%d",
+			core_info->core_index, ppp_res->res_state);
+		return -EINVAL;
+	}
+
+	rsrc_data = (struct cam_tfe_ppp_data  *)ppp_res->res_priv;
+
+	/* Config tfe core */
+	val = (1 << rsrc_data->reg_data->pdaf_path_en_shift);
+
+	if (!rsrc_data->lcr_enable)
+		val = (1 << rsrc_data->reg_data->lcr_dis_en_shift);
+
+	if (rsrc_data->sync_mode != CAM_ISP_HW_SYNC_NONE)
+		val = (1 << rsrc_data->reg_data->lcr_dis_en_shift);
+
+	cam_io_w_mb(val, rsrc_data->mem_base +
+		rsrc_data->common_reg->core_cfg_0);
+
+	ppp_res->res_state = CAM_ISP_RESOURCE_STATE_STREAMING;
+
+	CAM_DBG(CAM_ISP, "TFE: %d Start PPP Done, core_cfg 0 val:0x%x",
+		core_info->core_index, val);
+	return 0;
+}
+
 int cam_tfe_top_start(struct cam_tfe_hw_core_info *core_info,
 	void *start_args, uint32_t arg_size)
 {
@@ -2182,6 +2493,7 @@ int cam_tfe_top_start(struct cam_tfe_hw_core_info *core_info,
 	top_priv = (struct cam_tfe_top_priv *)core_info->top_priv;
 	in_res = (struct cam_isp_resource_node *)start_args;
 	hw_info = (struct cam_hw_info  *)in_res->hw_intf->hw_priv;
+	atomic_set(&top_priv->switch_out_of_sync_cnt, 0);
 
 	if (hw_info->hw_state != CAM_HW_STATE_POWER_UP) {
 		CAM_ERR(CAM_ISP, "TFE:%d HW not powered up",
@@ -2190,6 +2502,7 @@ int cam_tfe_top_start(struct cam_tfe_hw_core_info *core_info,
 		goto end;
 	}
 
+	top_priv->last_mup_val = 0;
 	rc = cam_tfe_top_set_hw_clk_rate(top_priv);
 	if (rc) {
 		CAM_ERR(CAM_ISP, "TFE:%d set_hw_clk_rate failed, rc=%d",
@@ -2206,6 +2519,8 @@ int cam_tfe_top_start(struct cam_tfe_hw_core_info *core_info,
 
 	if (in_res->res_id == CAM_ISP_HW_TFE_IN_CAMIF) {
 		cam_tfe_camif_resource_start(core_info, in_res);
+	} else if (in_res->res_id == CAM_ISP_HW_TFE_IN_PDLIB) {
+		cam_tfe_ppp_resource_start(core_info, in_res);
 	} else if (in_res->res_id >= CAM_ISP_HW_TFE_IN_RDI0 &&
 		in_res->res_id <= CAM_ISP_HW_TFE_IN_RDI2) {
 		rsrc_rdi_data = (struct cam_tfe_rdi_data *) in_res->res_priv;
@@ -2275,6 +2590,7 @@ int cam_tfe_top_stop(struct cam_tfe_hw_core_info *core_info,
 	struct cam_hw_info                      *hw_info = NULL;
 	struct cam_tfe_camif_data               *camif_data;
 	struct cam_tfe_rdi_data                 *rsrc_rdi_data;
+	struct cam_tfe_ppp_data                 *ppp_data;
 	uint32_t val = 0;
 	int i, rc = 0;
 
@@ -2312,7 +2628,15 @@ int cam_tfe_top_stop(struct cam_tfe_hw_core_info *core_info,
 			cam_io_w_mb(val, camif_data->mem_base +
 				camif_data->common_reg->diag_config);
 		}
-	}  else if ((in_res->res_id >= CAM_ISP_HW_TFE_IN_RDI0) &&
+	}  else if (in_res->res_id == CAM_ISP_HW_TFE_IN_PDLIB) {
+		ppp_data = (struct cam_tfe_ppp_data *)in_res->res_priv;
+
+		cam_io_w_mb(0, ppp_data->mem_base +
+			ppp_data->ppp_reg->ppp_module_config);
+
+		if (in_res->res_state == CAM_ISP_RESOURCE_STATE_STREAMING)
+			in_res->res_state = CAM_ISP_RESOURCE_STATE_RESERVED;
+	} else if ((in_res->res_id >= CAM_ISP_HW_TFE_IN_RDI0) &&
 		(in_res->res_id <= CAM_ISP_HW_TFE_IN_RDI2)) {
 		rsrc_rdi_data = (struct cam_tfe_rdi_data *) in_res->res_priv;
 		cam_io_w_mb(0x0, rsrc_rdi_data->mem_base +
@@ -2345,6 +2669,7 @@ int cam_tfe_top_stop(struct cam_tfe_hw_core_info *core_info,
 		}
 	}
 
+	atomic_set(&top_priv->switch_out_of_sync_cnt, 0);
 	core_info->irq_err_config_cnt--;
 	if (!core_info->irq_err_config_cnt)
 		cam_tfe_irq_config(core_info,
@@ -2365,6 +2690,7 @@ int cam_tfe_top_init(
 	struct cam_tfe_soc_private        *soc_private = NULL;
 	struct cam_tfe_camif_data         *camif_priv = NULL;
 	struct cam_tfe_rdi_data           *rdi_priv = NULL;
+	struct cam_tfe_ppp_data           *ppp_priv = NULL;
 	int i, j, rc = 0;
 
 	top_priv = kzalloc(sizeof(struct cam_tfe_top_priv),
@@ -2427,6 +2753,29 @@ int cam_tfe_top_init(
 			camif_priv->hw_intf     = hw_intf;
 			camif_priv->soc_info    = soc_info;
 
+		} else if (hw_info->in_port[i] == CAM_TFE_PDLIB_VER_1_0) {
+			top_priv->in_rsrc[i].res_id =
+				CAM_ISP_HW_TFE_IN_PDLIB;
+
+			ppp_priv = kzalloc(sizeof(struct cam_tfe_ppp_data),
+					GFP_KERNEL);
+			if (!ppp_priv) {
+				CAM_DBG(CAM_ISP,
+					"TFE:%d Error Failed to alloc for ppp_priv",
+					core_info->core_index);
+				goto deinit_resources;
+			}
+
+			top_priv->in_rsrc[i].res_priv = ppp_priv;
+
+			ppp_priv->mem_base    =
+				soc_info->reg_map[TFE_CORE_BASE_IDX].mem_base;
+			ppp_priv->hw_intf     = hw_intf;
+			ppp_priv->common_reg  = hw_info->common_reg;
+			ppp_priv->ppp_reg     =
+				hw_info->ppp_hw_info.ppp_reg;
+			ppp_priv->reg_data    =
+				hw_info->ppp_hw_info.reg_data;
 		} else if (hw_info->in_port[i] ==
 			CAM_TFE_RDI_VER_1_0) {
 			top_priv->in_rsrc[i].res_id =
@@ -2975,6 +3324,10 @@ int cam_tfe_process_cmd(void *hw_priv, uint32_t cmd_type,
 			core_info->tfe_bus->bus_priv, cmd_type, cmd_args,
 			arg_size);
 		break;
+	case CAM_ISP_HW_CMD_GET_PATH_PORT_MAP:
+		rc = cam_tfe_bus_get_path_port_map(hw_info->top_hw_info, cmd_args,
+					arg_size);
+		break;
 	default:
 		CAM_ERR(CAM_ISP, "TFE:%d Invalid cmd type:%d",
 			core_info->core_index, cmd_type);

+ 75 - 8
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_core.h

@@ -1,6 +1,7 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 /*
  * Copyright (c) 2019-2021, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2022-2023, Qualcomm Innovation Center, Inc. All rights reserved.
  */
 
 
@@ -15,20 +16,22 @@
 
 #define CAM_TFE_CAMIF_VER_1_0        0x10
 #define CAM_TFE_RDI_VER_1_0          0x1000
+#define CAM_TFE_PDLIB_VER_1_0        0x10000
 #define CAM_TFE_TOP_1_0              0x1000
-#define CAM_TFE_TOP_IN_PORT_MAX      4
+#define CAM_TFE_TOP_IN_PORT_MAX      5
 #define CAM_TFE_RDI_MAX              4
 
 #define CAMIF_DEBUG_ENABLE_SENSOR_DIAG_STATUS      BIT(0)
 #define CAM_TFE_EVT_MAX                            256
 
-#define CAM_TFE_MAX_REG_DUMP_ENTRIES  20
-#define CAM_TFE_MAX_LUT_DUMP_ENTRIES  10
+#define CAM_TFE_MAX_REG_DUMP_ENTRIES        20
+#define CAM_TFE_MAX_LUT_DUMP_ENTRIES        10
 
-#define CAM_TFE_MAX_CLC               40
-#define CAM_TFE_CLC_NAME_LENGTH_MAX   32
-#define CAM_TFE_MAX_DEBUG_REG         10
-#define CAM_TFE_MAX_PERF_CNT           2
+#define CAM_TFE_MAX_CLC                     42
+#define CAM_TFE_CLC_NAME_LENGTH_MAX         32
+#define CAM_TFE_LITE_MAX_CLC                4
+#define CAM_TFE_MAX_DEBUG_REG               12
+#define CAM_TFE_MAX_PERF_CNT                2
 
 /*we take each word as uint32_t, for dumping uint64_t count as 2 words
  * soc index
@@ -85,7 +88,8 @@ struct cam_tfe_top_reg_offset_common {
 	uint32_t stats_feature;
 	uint32_t zoom_feature;
 	uint32_t global_reset_cmd;
-	uint32_t core_cgc_ctrl;
+	uint32_t core_cgc_ctrl_0;
+	uint32_t core_cgc_ctrl_1;
 	uint32_t ahb_cgc_ctrl;
 	uint32_t core_cfg_0;
 	uint32_t core_cfg_1;
@@ -102,14 +106,41 @@ struct cam_tfe_top_reg_offset_common {
 	uint32_t debug_cfg;
 	uint32_t num_perf_cfg;
 	struct   cam_tfe_top_reg_perf_cfg perf_cfg[CAM_TFE_MAX_PERF_CNT];
+	uint32_t diag_sensor_frame_cnt_status_1;
 
 	/*reg data */
 	uint32_t diag_min_hbi_error_shift;
 	uint32_t diag_neq_hbi_shift;
 	uint32_t diag_sensor_hbi_mask;
+	uint32_t mup_shift_val;
+
+	/* error bit data */
+	uint32_t pp_camif_violation_bit;
+	uint32_t pp_violation_bit;
+	uint32_t ppp_camif_violation_bit;
+	uint32_t ppp_violation_bit;
+	uint32_t rdi0_camif_violation_bit;
+	uint32_t rdi1_camif_violation_bit;
+	uint32_t rdi2_camif_violation_bit;
+	uint32_t diag_violation_bit;
+	uint32_t dyamanic_switch_violation_bit;
+	uint32_t pp_frame_drop_bit;
+	uint32_t ppp_frame_drop_bit;
+	uint32_t rdi0_frame_drop_bit;
+	uint32_t rdi1_frame_drop_bit;
+	uint32_t rdi2_frame_drop_bit;
+	uint32_t pp_overflow_bit;
+	uint32_t ppp_overflow_bit;
+	uint32_t rdi0_overflow_bit;
+	uint32_t rdi1_overflow_bit;
+	uint32_t rdi2_overflow_bit;
+	uint32_t out_of_sync_frame_drop_bit;
+	uint32_t height_shift;
+	uint32_t epoch_shift_val;
 
 	/* configuration */
 	bool serializer_supported;
+	bool mup_supported;
 };
 
 struct cam_tfe_camif_reg {
@@ -211,6 +242,34 @@ struct cam_tfe_rdi_reg_data {
 	uint32_t     diag_sensor_shift;
 };
 
+struct cam_tfe_ppp_reg {
+	uint32_t     ppp_hw_version;
+	uint32_t     ppp_hw_status;
+	uint32_t     ppp_module_config;
+	uint32_t     ppp_skip_period;
+	uint32_t     ppp_irq_subsample_pattern;
+	uint32_t     ppp_epoch_irq;
+	uint32_t     ppp_debug_1;
+	uint32_t     ppp_debug_0;
+	uint32_t     ppp_test_bus_ctrl;
+	uint32_t     ppp_spare;
+	uint32_t     reg_update_cmd;
+};
+
+struct cam_tfe_ppp_reg_data {
+	uint32_t     sof_irq_mask;
+	uint32_t     epoch0_irq_mask;
+	uint32_t     epoch1_irq_mask;
+	uint32_t     eof_irq_mask;
+	uint32_t     subscribe_irq_mask[CAM_TFE_TOP_IRQ_REG_NUM];
+	uint32_t     enable_diagnostic_hw;
+	uint32_t     diag_sensor_sel;
+	uint32_t     diag_sensor_shift;
+
+	uint32_t     pdaf_path_en_shift;
+	uint32_t     lcr_dis_en_shift;
+};
+
 struct cam_tfe_clc_hw_status {
 	uint8_t     name[CAM_TFE_CLC_NAME_LENGTH_MAX];
 	uint32_t    hw_status_reg;
@@ -221,12 +280,20 @@ struct cam_tfe_rdi_hw_info {
 	struct cam_tfe_rdi_reg_data         *reg_data;
 };
 
+struct cam_tfe_ppp_hw_info {
+	struct cam_tfe_ppp_reg              *ppp_reg;
+	struct cam_tfe_ppp_reg_data         *reg_data;
+};
+
 struct cam_tfe_top_hw_info {
 	struct cam_tfe_top_reg_offset_common  *common_reg;
 	struct cam_tfe_camif_hw_info           camif_hw_info;
 	struct cam_tfe_rdi_hw_info             rdi_hw_info[CAM_TFE_RDI_MAX];
+	struct cam_tfe_ppp_hw_info             ppp_hw_info;
 	uint32_t in_port[CAM_TFE_TOP_IN_PORT_MAX];
 	struct cam_tfe_reg_dump_data           reg_dump_data;
+	uint32_t                               num_path_port_map;
+	uint32_t path_port_map[CAM_ISP_HW_PATH_PORT_MAP_MAX][2];
 };
 
 struct cam_tfe_hw_info {

+ 580 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_lite770.h

@@ -0,0 +1,580 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+/*
+ * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
+ */
+
+
+#ifndef _CAM_TFE_LITE770_H_
+#define _CAM_TFE_LITE770_H_
+#include "cam_tfe_core.h"
+#include "cam_tfe_bus.h"
+
+
+/* throtle cfg register not used, diag sensor frame cnt status1 */
+static struct cam_tfe_top_reg_offset_common  tfe_lite770_top_commong_reg  = {
+	.hw_version                             = 0x00001800,
+	.hw_capability                          = 0x00001804,
+	.lens_feature                           = 0x00001808,
+	.stats_feature                          = 0x0000180C,
+	.zoom_feature                           = 0x00001810,
+	.global_reset_cmd                       = 0x00001814,
+	.core_cgc_ctrl_0                        = 0x00001818,
+	.core_cgc_ctrl_1                        = 0x0000181C,
+	.ahb_cgc_ctrl                           = 0x00001820,
+	.core_cfg_0                             = 0x00001824,
+	.reg_update_cmd                         = 0x0000182C,
+	.diag_config                            = 0x00001860,
+	.diag_sensor_status_0                   = 0x00001864,
+	.diag_sensor_status_1                   = 0x00001868,
+	.diag_sensor_frame_cnt_status           = 0x0000186C,
+	.violation_status                       = 0x00001870,
+	.stats_throttle_cnt_cfg_0               = 0x00001874,
+	.stats_throttle_cnt_cfg_1               = 0x00001878,
+	.num_debug_reg                          = 12,
+	.debug_reg = {
+		0x000018A0,
+		0x000018A4,
+		0x000018A8,
+		0x000018AC,
+		0x000018B0,
+		0x000018B4,
+		0x000018B8,
+		0x000018BC,
+		0x000018C0,
+		0x000018C4,
+		0x000018C8,
+		0x000018CC,
+	},
+	.debug_cfg                              = 0x000018DC,
+	.num_perf_cfg                           = 2,
+	.perf_cfg = {
+		{
+			.perf_cnt_cfg           = 0x000018E0,
+			.perf_pixel_count       = 0x000018E4,
+			.perf_line_count        = 0x000018E8,
+			.perf_stall_count       = 0x000018EC,
+			.perf_always_count      = 0x000018F0,
+			.perf_count_status      = 0x000018F4,
+		},
+		{
+			.perf_cnt_cfg           = 0x000018F8,
+			.perf_pixel_count       = 0x000018FC,
+			.perf_line_count        = 0x00001900,
+			.perf_stall_count       = 0x00001904,
+			.perf_always_count      = 0x00001908,
+			.perf_count_status      = 0x0000190C,
+		},
+	},
+	.diag_sensor_frame_cnt_status_1         = 0x00001920,
+	.diag_min_hbi_error_shift               = 15,
+	.diag_neq_hbi_shift                     = 14,
+	.diag_sensor_hbi_mask                   = 0x3FFF,
+	.serializer_supported                   = true,
+};
+
+static struct cam_tfe_rdi_reg  tfe_lite770_rdi0_reg = {
+	.rdi_hw_version              = 0x00001E00,
+	.rdi_hw_status               = 0x00001E04,
+	.rdi_module_config           = 0x00001E60,
+	.rdi_skip_period             = 0x00001E68,
+	.rdi_irq_subsample_pattern   = 0x00001E6C,
+	.rdi_epoch_irq               = 0x00001E70,
+	.rdi_debug_1                 = 0x00001FF0,
+	.rdi_debug_0                 = 0x00001FF4,
+	.rdi_test_bus_ctrl           = 0x00001FF8,
+	.rdi_spare                   = 0x00001FFC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_rdi_reg_data tfe_lite770_rdi0_reg_data = {
+	.reg_update_cmd_data         = 0x2,
+	.epoch_line_cfg              = 0x00140014,
+	.pixel_pattern_shift         = 24,
+	.pixel_pattern_mask          = 0x07000000,
+	.rdi_out_enable_shift        = 0,
+
+	.sof_irq_mask                = 0x00000010,
+	.epoch0_irq_mask             = 0x00000040,
+	.epoch1_irq_mask             = 0x00000080,
+	.eof_irq_mask                = 0x00000020,
+	.error_irq_mask0             = 0x00020200,
+	.error_irq_mask2             = 0x00000004,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00000030,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x1,
+	.diag_sensor_shift           = 0x1,
+};
+
+static struct cam_tfe_rdi_reg  tfe_lite770_rdi1_reg = {
+	.rdi_hw_version              = 0x00002000,
+	.rdi_hw_status               = 0x00002004,
+	.rdi_module_config           = 0x00002060,
+	.rdi_skip_period             = 0x00002068,
+	.rdi_irq_subsample_pattern   = 0x0000206C,
+	.rdi_epoch_irq               = 0x00002070,
+	.rdi_debug_1                 = 0x000021F0,
+	.rdi_debug_0                 = 0x000021F4,
+	.rdi_test_bus_ctrl           = 0x000021F8,
+	.rdi_spare                   = 0x000021FC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_rdi_reg_data tfe_lite770_rdi1_reg_data = {
+	.reg_update_cmd_data         = 0x4,
+	.epoch_line_cfg              = 0x00140014,
+	.pixel_pattern_shift         = 24,
+	.pixel_pattern_mask          = 0x07000000,
+	.rdi_out_enable_shift        = 0,
+
+	.sof_irq_mask                = 0x00000100,
+	.epoch0_irq_mask             = 0x00000400,
+	.epoch1_irq_mask             = 0x00000800,
+	.eof_irq_mask                = 0x00000200,
+	.error_irq_mask0             = 0x00040400,
+	.error_irq_mask2             = 0x00000008,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00000300,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x2,
+	.diag_sensor_shift           = 0x1,
+};
+
+static struct cam_tfe_rdi_reg  tfe_lite770_rdi2_reg = {
+	.rdi_hw_version              = 0x00002200,
+	.rdi_hw_status               = 0x00002204,
+	.rdi_module_config           = 0x00002260,
+	.rdi_skip_period             = 0x00002268,
+	.rdi_irq_subsample_pattern   = 0x0000226C,
+	.rdi_epoch_irq               = 0x00002270,
+	.rdi_debug_1                 = 0x000023F0,
+	.rdi_debug_0                 = 0x000023F4,
+	.rdi_test_bus_ctrl           = 0x000023F8,
+	.rdi_spare                   = 0x000023FC,
+	.reg_update_cmd              = 0x0000182C,
+};
+
+static struct cam_tfe_rdi_reg_data tfe_lite770_rdi2_reg_data = {
+	.reg_update_cmd_data         = 0x8,
+	.epoch_line_cfg              = 0x00140014,
+	.pixel_pattern_shift         = 24,
+	.pixel_pattern_mask          = 0x07000000,
+	.rdi_out_enable_shift        = 0,
+
+	.sof_irq_mask                = 0x00001000,
+	.epoch0_irq_mask             = 0x00004000,
+	.epoch1_irq_mask             = 0x00008000,
+	.eof_irq_mask                = 0x00002000,
+	.error_irq_mask0             = 0x00080800,
+	.error_irq_mask2             = 0x00000004,
+	.subscribe_irq_mask          = {
+		0x00000000,
+		0x00003000,
+		0x00000000,
+	},
+	.enable_diagnostic_hw        = 0x1,
+	.diag_sensor_sel             = 0x3,
+	.diag_sensor_shift           = 0x1,
+
+};
+
+static struct cam_tfe_clc_hw_status  tfe_lite770_clc_hw_info[CAM_TFE_LITE_MAX_CLC] = {
+	{
+		.name = "CLC_RDI0_CAMIF",
+		.hw_status_reg = 0x1E04,
+	},
+	{
+		.name = "CLC_RDI1_CAMIF",
+		.hw_status_reg = 0x2004,
+	},
+	{
+		.name = "CLC_RDI2_CAMIF",
+		.hw_status_reg = 0x2204,
+	},
+};
+
+static struct  cam_tfe_top_hw_info tfe_lite770_top_hw_info = {
+	.common_reg = &tfe_lite770_top_commong_reg,
+	.rdi_hw_info  = {
+		{
+			.rdi_reg  = &tfe_lite770_rdi0_reg,
+			.reg_data = &tfe_lite770_rdi0_reg_data,
+		},
+		{
+			.rdi_reg  = &tfe_lite770_rdi1_reg,
+			.reg_data = &tfe_lite770_rdi1_reg_data,
+		},
+		{
+			.rdi_reg  = &tfe_lite770_rdi2_reg,
+			.reg_data = &tfe_lite770_rdi2_reg_data,
+		},
+	},
+	.in_port = {
+		CAM_TFE_RDI_VER_1_0,
+		CAM_TFE_RDI_VER_1_0,
+		CAM_TFE_RDI_VER_1_0
+	},
+	.reg_dump_data  = {
+		.num_reg_dump_entries    = 19,
+		.num_lut_dump_entries    = 0,
+		.bus_start_addr          = 0x2000,
+		.bus_write_top_end_addr  = 0x2120,
+		.bus_client_start_addr   = 0x2200,
+		.bus_client_offset       = 0x100,
+		.num_bus_clients         = 10,
+		.reg_entry = {
+			{
+				.start_offset = 0x1000,
+				.end_offset   = 0x10F4,
+			},
+			{
+				.start_offset = 0x1260,
+				.end_offset   = 0x1280,
+			},
+			{
+				.start_offset = 0x13F0,
+				.end_offset   = 0x13FC,
+			},
+			{
+				.start_offset = 0x1460,
+				.end_offset   = 0x1470,
+			},
+			{
+				.start_offset = 0x15F0,
+				.end_offset   = 0x15FC,
+			},
+			{
+				.start_offset = 0x1660,
+				.end_offset   = 0x1670,
+			},
+			{
+				.start_offset = 0x17F0,
+				.end_offset   = 0x17FC,
+			},
+			{
+				.start_offset = 0x1860,
+				.end_offset   = 0x1870,
+			},
+			{
+				.start_offset = 0x19F0,
+				.end_offset   = 0x19FC,
+			},
+			{
+				.start_offset = 0x2660,
+				.end_offset   = 0x2694,
+			},
+			{
+				.start_offset = 0x2860,
+				.end_offset   = 0x2884,
+			},
+			{
+				.start_offset = 0x2A60,
+				.end_offset   = 0X2B34,
+			},
+			{
+				.start_offset = 0x2C60,
+				.end_offset   = 0X2C80,
+			},
+			{
+				.start_offset = 0x2E60,
+				.end_offset   = 0X2E7C,
+			},
+			{
+				.start_offset = 0x3060,
+				.end_offset   = 0X3110,
+			},
+			{
+				.start_offset = 0x3260,
+				.end_offset   = 0X3278,
+			},
+			{
+				.start_offset = 0x3460,
+				.end_offset   = 0X3478,
+			},
+			{
+				.start_offset = 0x3660,
+				.end_offset   = 0X3684,
+			},
+			{
+				.start_offset = 0x3860,
+				.end_offset   = 0X3884,
+			},
+		},
+		.lut_entry = {
+			{
+				.lut_word_size = 1,
+				.lut_bank_sel  = 0x40,
+				.lut_addr_size = 180,
+				.dmi_reg_offset = 0x2800,
+			},
+			{
+				.lut_word_size = 1,
+				.lut_bank_sel  = 0x41,
+				.lut_addr_size = 180,
+				.dmi_reg_offset = 0x3000,
+			},
+		},
+	},
+};
+
+static struct cam_tfe_bus_hw_info  tfe_lite770_bus_hw_info = {
+	.common_reg = {
+		.hw_version  = 0x00003000,
+		.cgc_ovd     = 0x00003008,
+		.comp_cfg_0  = 0x0000300C,
+		.comp_cfg_1  = 0x00003010,
+		.frameheader_cfg  = {
+			0x00003034,
+			0x00003038,
+			0x0000303C,
+			0x00003040,
+		},
+		.pwr_iso_cfg = 0x0000305C,
+		.overflow_status_clear = 0x00003060,
+		.ccif_violation_status = 0x00003064,
+		.overflow_status       = 0x00003068,
+		.image_size_violation_status = 0x00003070,
+		.perf_count_cfg = {
+			0x00003074,
+			0x00003078,
+			0x0000307C,
+			0x00003080,
+			0x00003084,
+			0x00003088,
+			0x0000308C,
+			0x00003090,
+		},
+		.perf_count_val = {
+			0x00003094,
+			0x00003098,
+			0x0000309C,
+			0x000030A0,
+			0x000030A4,
+			0x000030A8,
+			0x000030AC,
+			0x000030B0,
+		},
+		.perf_count_status = 0x000030B4,
+		.debug_status_top_cfg = 0x000030D4,
+		.debug_status_top = 0x000030D8,
+		.test_bus_ctrl = 0x000030DC,
+		.irq_mask = {
+			0x00003018,
+			0x0000301C,
+		},
+		.irq_clear = {
+			0x00003020,
+			0x00003024,
+		},
+		.irq_status = {
+			0x00003028,
+			0x0000302C,
+		},
+		.irq_cmd = 0x00003030,
+		.cons_violation_shift = 28,
+		.violation_shift  = 30,
+		.image_size_violation = 31,
+	},
+	.num_client = 3,
+	.bus_client_reg = {
+		{
+			.cfg                   = 0x00003900,
+			.image_addr            = 0x00003904,
+			.frame_incr            = 0x00003908,
+			.image_cfg_0           = 0x0000390C,
+			.image_cfg_1           = 0x00003910,
+			.image_cfg_2           = 0x00003914,
+			.packer_cfg            = 0x00003918,
+			.bw_limit              = 0x0000391C,
+			.frame_header_addr     = 0x00003920,
+			.frame_header_incr     = 0x00003924,
+			.frame_header_cfg      = 0x00003928,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003930,
+			.irq_subsample_pattern = 0x00003934,
+			.framedrop_period      = 0x00003938,
+			.framedrop_pattern     = 0x0000393C,
+			.system_cache_cfg     = 0x00003960,
+			.addr_status_0         = 0x00003968,
+			.addr_status_1         = 0x0000396C,
+			.addr_status_2         = 0x00003970,
+			.addr_status_3         = 0x00003974,
+			.debug_status_cfg      = 0x00003978,
+			.debug_status_0        = 0x0000397C,
+			.debug_status_1        = 0x00003980,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_0,
+			.client_name           = "RDI0",
+		},
+		/* BUS Client 8 RDI1 */
+		{
+			.cfg                   = 0x00003A00,
+			.image_addr            = 0x00003A04,
+			.frame_incr            = 0x00003A08,
+			.image_cfg_0           = 0x00003A0C,
+			.image_cfg_1           = 0x00003A10,
+			.image_cfg_2           = 0x00003A14,
+			.packer_cfg            = 0x00003A18,
+			.bw_limit              = 0x00003A1C,
+			.frame_header_addr     = 0x00003A20,
+			.frame_header_incr     = 0x00003A24,
+			.frame_header_cfg      = 0x00003A28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003A30,
+			.irq_subsample_pattern = 0x00003A34,
+			.framedrop_period      = 0x00003A38,
+			.framedrop_pattern     = 0x00003A3C,
+			.system_cache_cfg     = 0x00003A60,
+			.addr_status_0         = 0x00003A68,
+			.addr_status_1         = 0x00003A6C,
+			.addr_status_2         = 0x00003A70,
+			.addr_status_3         = 0x00003A74,
+			.debug_status_cfg      = 0x00003A78,
+			.debug_status_0        = 0x00003A7C,
+			.debug_status_1        = 0x00003A80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_1,
+			.client_name           = "RDI1",
+		},
+		/* BUS Client 9 RDI2 */
+		{
+			.cfg                   = 0x00003B00,
+			.image_addr            = 0x00003B04,
+			.frame_incr            = 0x00003B08,
+			.image_cfg_0           = 0x00003B0C,
+			.image_cfg_1           = 0x00003B10,
+			.image_cfg_2           = 0x00003B14,
+			.packer_cfg            = 0x00003B18,
+			.bw_limit              = 0x00003B1C,
+			.frame_header_addr     = 0x00003B20,
+			.frame_header_incr     = 0x00003B24,
+			.frame_header_cfg      = 0x00003B28,
+			.line_done_cfg         = 0x00000000,
+			.irq_subsample_period  = 0x00003B30,
+			.irq_subsample_pattern = 0x00003B34,
+			.framedrop_period      = 0x00003B38,
+			.framedrop_pattern     = 0x00003B3C,
+			.system_cache_cfg     = 0x00003B60,
+			.addr_status_0         = 0x00003B68,
+			.addr_status_1         = 0x00003B6C,
+			.addr_status_2         = 0x00003B70,
+			.addr_status_3         = 0x00003B74,
+			.debug_status_cfg      = 0x00003B78,
+			.debug_status_0        = 0x00003B7C,
+			.debug_status_1        = 0x00003B80,
+			.comp_group            = CAM_TFE_BUS_COMP_GRP_2,
+			.client_name           = "RDI2",
+		},
+	},
+	.num_out  = 3,
+	.tfe_out_hw_info = {
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RDI0,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_0,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_1,
+			.mid[0]              = 4,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RDI1,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_1,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_2,
+			.mid[0]              = 5,
+		},
+		{
+			.tfe_out_id       = CAM_TFE_BUS_TFE_OUT_RDI2,
+			.max_width        = -1,
+			.max_height       = -1,
+			.composite_group  = CAM_TFE_BUS_COMP_GRP_2,
+			.rup_group_id     = CAM_TFE_BUS_RUP_GRP_3,
+			.mid[0]              = 6,
+		},
+	},
+	.num_comp_grp             = 3,
+	.max_wm_per_comp_grp      = 3,
+	.comp_done_shift          = 8,
+	.top_bus_wr_irq_shift     = 1,
+	.comp_buf_done_mask = 0x7FF00,
+	.comp_rup_done_mask = 0xF,
+	.bus_irq_error_mask = {
+		0xD0000000,
+		0x00000000,
+	},
+	.support_consumed_addr = true,
+	.pdaf_rdi2_mux_en = false,
+	.rdi_width = 128,
+};
+
+struct cam_tfe_hw_info cam_tfe_lite770 = {
+	.top_irq_mask = {
+		0x00001834,
+		0x00001838,
+		0x0000183C,
+	},
+	.top_irq_clear = {
+		0x00001840,
+		0x00001844,
+		0x00001848,
+	},
+	.top_irq_status = {
+		0x0000184C,
+		0x00001850,
+		0x00001854,
+	},
+	.top_irq_cmd                       = 0x00001830,
+	.global_clear_bitmask              = 0x00000001,
+	.bus_irq_mask = {
+		0x00003018,
+		0x0000301C,
+	},
+	.bus_irq_clear = {
+		0x00003020,
+		0x00003024,
+	},
+	.bus_irq_status = {
+		0x00003028,
+		0x0000302C,
+	},
+	.bus_irq_cmd = 0x00003030,
+	.bus_violation_reg = 0x00003064,
+	.bus_overflow_reg = 0x00003068,
+	.bus_image_size_vilation_reg = 0x3070,
+	.bus_overflow_clear_cmd = 0x3060,
+	.debug_status_top = 0x30D8,
+
+	.reset_irq_mask = {
+		0x00000001,
+		0x00000000,
+		0x00000000,
+	},
+	.error_irq_mask = {
+		0x000F0F00,
+		0x00000000,
+		0x0000003F,
+	},
+	.bus_reg_irq_mask = {
+		0x00000002,
+		0x00000000,
+	},
+	.bus_error_irq_mask = {
+		0xC0000000,
+		0x00000000,
+	},
+
+	.num_clc = 3,
+	.clc_hw_status_info            = tfe_lite770_clc_hw_info,
+	.bus_version                   = CAM_TFE_BUS_1_0,
+	.bus_hw_info                   = &tfe_lite770_bus_hw_info,
+
+	.top_version                   = CAM_TFE_TOP_1_0,
+	.top_hw_info                   = &tfe_lite770_top_hw_info,
+};
+
+#endif /* _CAM_TFE_LITE770__H_ */

+ 5 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_soc.c

@@ -45,6 +45,11 @@ int cam_tfe_init_soc_resources(struct cam_hw_soc_info *soc_info,
 		goto free_soc_private;
 	}
 
+	soc_private->is_tfe_lite = false;
+	if (strnstr(soc_info->compatible, "lite",
+		strlen(soc_info->compatible)) != NULL)
+		soc_private->is_tfe_lite = true;
+
 	/* set some default values */
 	soc_private->num_pid = 0;
 

+ 2 - 0
drivers/cam_isp/isp_hw_mgr/isp_hw/tfe_hw/cam_tfe_soc.h

@@ -30,6 +30,7 @@ enum cam_cpas_handle_id {
  * @dsp_clk_index:           DSP clk index in optional clocks
  * @num_pid:                 number of pids of tfe
  * @pid:                     TFE pid value list
+ * @is_tfe_lite:             Flag to indicate if it is TFE Lite HW
  */
 struct cam_tfe_soc_private {
 	uint32_t    cpas_handle;
@@ -37,6 +38,7 @@ struct cam_tfe_soc_private {
 	int32_t     dsp_clk_index;
 	uint32_t    num_pid;
 	uint32_t    pid[CAM_ISP_HW_MAX_PID_VAL];
+	bool        is_tfe_lite;
 };
 
 /*

+ 1 - 0
include/uapi/camera/media/cam_tfe.h

@@ -73,6 +73,7 @@
 #define CAM_ISP_TFE_GENERIC_BLOB_TYPE_BW_CONFIG_V2        2
 #define CAM_ISP_TFE_GENERIC_BLOB_TYPE_CSID_CLOCK_CONFIG   3
 #define CAM_ISP_TFE_GENERIC_BLOB_TYPE_BW_LIMITER_CFG      16
+#define CAM_ISP_TFE_GENERIC_BLOB_TYPE_DYNAMIC_MODE_SWITCH 15
 
 /* DSP mode */
 #define CAM_ISP_TFE_DSP_MODE_NONE                   0