From 131b4115d56367bd8482378bcdae6879ac116b74 Mon Sep 17 00:00:00 2001 From: Venkat Chinta Date: Thu, 30 Jan 2020 12:43:55 -0800 Subject: [PATCH] msm: camera: isp: Add support for PHY TPG This change adds support for PHY TPG version 102 hardware. CRs-Fixed: 2608550 Change-Id: I92387b08e8a91bb0c6a77b5301ebc30c7cb6f252 Signed-off-by: Vishalsingh Hajeri Signed-off-by: Venkat Chinta Signed-off-by: Mukund Madhusudan Atre --- drivers/Makefile | 9 +- drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c | 92 +++++ drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.h | 6 + drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c | 2 +- .../isp_hw/ife_csid_hw/cam_ife_csid_core.c | 18 +- .../isp_hw/include/cam_top_tpg_hw_intf.h | 19 +- .../isp_hw_mgr/isp_hw/top_tpg/Makefile | 15 - .../isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.c | 48 +++ .../isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.h | 12 + .../{cam_top_tpg_v1.h => cam_top_tpg101.h} | 17 +- .../isp_hw/top_tpg/cam_top_tpg102.h | 50 +++ .../isp_hw/top_tpg/cam_top_tpg_core.c | 383 +---------------- .../isp_hw/top_tpg/cam_top_tpg_core.h | 70 +--- .../isp_hw/top_tpg/cam_top_tpg_dev.c | 46 +-- .../isp_hw/top_tpg/cam_top_tpg_v1.c | 54 --- .../isp_hw/top_tpg/cam_top_tpg_ver1.c | 385 ++++++++++++++++++ .../isp_hw/top_tpg/cam_top_tpg_ver1.h | 55 +++ .../isp_hw/top_tpg/cam_top_tpg_ver2.c | 242 +++++++++++ .../isp_hw/top_tpg/cam_top_tpg_ver2.h | 44 ++ drivers/camera_main.c | 8 +- drivers/camera_main.h | 3 +- include/uapi/camera/media/cam_isp_ife.h | 6 +- 22 files changed, 1055 insertions(+), 529 deletions(-) delete mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/Makefile create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.c create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.h rename drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/{cam_top_tpg_v1.h => cam_top_tpg101.h} (76%) create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg102.h delete mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.c create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.c create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.h create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.c create mode 100644 drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.h diff --git a/drivers/Makefile b/drivers/Makefile index 8f4432bf6d..2ab203025f 100644 --- a/drivers/Makefile +++ b/drivers/Makefile @@ -85,6 +85,11 @@ camera-$(CONFIG_SPECTRA_ISP) += \ cam_isp/isp_hw_mgr/isp_hw/vfe_hw/vfe_top/cam_vfe_fe_ver1.o \ cam_isp/isp_hw_mgr/isp_hw/vfe_hw/vfe_top/cam_vfe_camif_lite_ver3.o \ cam_isp/isp_hw_mgr/isp_hw/vfe_hw/vfe17x/cam_vfe.o \ + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_dev.o \ + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_soc.o \ + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.o \ + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.o \ + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.o \ cam_isp/isp_hw_mgr/cam_isp_hw_mgr.o \ cam_isp/isp_hw_mgr/cam_ife_hw_mgr.o \ cam_isp/cam_isp_dev.o \ @@ -197,7 +202,9 @@ camera-$(CONFIG_SPECTRA_CAMERA) += \ cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_dev.o \ cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_soc.o \ cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.o \ - cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.o + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.o \ + cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.o + camera-y += camera_main.o diff --git a/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c b/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c index e2a2cecf72..c6e5e9d752 100644 --- a/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c +++ b/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.c @@ -424,6 +424,17 @@ static int cam_ife_hw_mgr_init_hw( struct cam_isp_hw_mgr_res *hw_mgr_res; int rc = 0, i; + if (ctx->is_tpg) { + CAM_DBG(CAM_ISP, "INIT TPG ... in ctx id:%d", + ctx->ctx_index); + rc = cam_ife_hw_mgr_init_hw_res(&ctx->res_list_tpg); + if (rc) { + CAM_ERR(CAM_ISP, "Can not INIT TFE TPG(id :%d)", + ctx->res_list_tpg.hw_res[0]->hw_intf->hw_idx); + goto deinit; + } + } + CAM_DBG(CAM_ISP, "INIT IFE CID ... in ctx id:%d", ctx->ctx_index); /* INIT IFE CID */ @@ -840,6 +851,10 @@ static int cam_ife_hw_mgr_release_hw_for_ctx( cam_ife_hw_mgr_put_res(&ife_ctx->free_res_list, &hw_mgr_res); } + /* ife phy tpg resource */ + if (ife_ctx->is_tpg) + cam_ife_hw_mgr_free_hw_res(&ife_ctx->res_list_tpg); + /* ife root node */ if (ife_ctx->res_list_ife_in.res_type != CAM_ISP_RESOURCE_UNINT) cam_ife_hw_mgr_free_hw_res(&ife_ctx->res_list_ife_in); @@ -1862,6 +1877,48 @@ end: } +static int cam_ife_hw_mgr_acquire_tpg( + struct cam_ife_hw_mgr_ctx *ife_ctx, + struct cam_isp_in_port_generic_info *in_port, + uint32_t num_inport) +{ + int rc = -EINVAL; + uint32_t i; + struct cam_ife_hw_mgr *ife_hw_mgr; + struct cam_hw_intf *hw_intf; + struct cam_top_tpg_ver2_reserve_args tpg_reserve; + + ife_hw_mgr = ife_ctx->hw_mgr; + + for (i = 0; i < CAM_TOP_TPG_HW_NUM_MAX; i++) { + if (!ife_hw_mgr->tpg_devices[i]) + continue; + + hw_intf = ife_hw_mgr->tpg_devices[i]; + tpg_reserve.num_inport = num_inport; + tpg_reserve.node_res = NULL; + tpg_reserve.in_port = in_port; + + rc = hw_intf->hw_ops.reserve(hw_intf->hw_priv, + &tpg_reserve, sizeof(tpg_reserve)); + if (!rc) + break; + } + + if (i == CAM_TOP_TPG_HW_NUM_MAX || !tpg_reserve.node_res) { + CAM_ERR(CAM_ISP, "Can not acquire IFE TPG"); + rc = -EINVAL; + goto end; + } + + ife_ctx->res_list_tpg.res_type = in_port->res_type; + ife_ctx->res_list_tpg.hw_res[0] = tpg_reserve.node_res; + ife_ctx->is_tpg = true; + +end: + return rc; +} + static int cam_ife_hw_mgr_acquire_res_ife_csid_pxl( struct cam_ife_hw_mgr_ctx *ife_ctx, struct cam_isp_in_port_generic_info *in_port, @@ -2755,6 +2812,16 @@ static int cam_ife_mgr_acquire_hw(void *hw_mgr_priv, void *acquire_hw_args) ife_ctx->use_frame_header_ts = true; } + if ((in_port->res_type == CAM_ISP_IFE_IN_RES_CPHY_TPG_0) || + (in_port->res_type == CAM_ISP_IFE_IN_RES_CPHY_TPG_1)) + rc = cam_ife_hw_mgr_acquire_tpg(ife_ctx, in_port, + acquire_hw_info->num_inputs); + + if (rc) { + CAM_ERR(CAM_ISP, "can not acquire TPG resource"); + goto free_mem; + } + rc = cam_ife_mgr_acquire_hw_for_ctx(ife_ctx, in_port, &num_pix_port_per_in, &num_rdi_port_per_in, &acquire_args->acquired_hw_id[i], @@ -3752,6 +3819,9 @@ static int cam_ife_mgr_stop_hw(void *hw_mgr_priv, void *stop_hw_args) if (cam_cdm_stream_off(ctx->cdm_handle)) CAM_ERR(CAM_ISP, "CDM stream off failed %d", ctx->cdm_handle); + if (ctx->is_tpg) + cam_ife_hw_mgr_stop_hw_res(&ctx->res_list_tpg); + cam_ife_hw_mgr_deinit_hw(ctx); CAM_DBG(CAM_ISP, "Stop success for ctx id:%d rc :%d", ctx->ctx_index, rc); @@ -4077,6 +4147,17 @@ start_only: } } + if (ctx->is_tpg) { + CAM_DBG(CAM_ISP, "START TPG HW ... in ctx id:%d", + ctx->ctx_index); + rc = cam_ife_hw_mgr_start_hw_res(&ctx->res_list_tpg, ctx); + if (rc) { + CAM_ERR(CAM_ISP, "Can not start IFE TPG (%d)", + ctx->res_list_tpg.res_id); + goto err; + } + } + /* Start IFE root node: do nothing */ CAM_DBG(CAM_ISP, "Start success for ctx id:%d", ctx->ctx_index); @@ -7100,6 +7181,16 @@ int cam_ife_hw_mgr_init(struct cam_hw_mgr_intf *hw_mgr_intf, int *iommu_hdl) return -EINVAL; } + /* fill tpg hw intf information */ + for (i = 0, j = 0; i < CAM_TOP_TPG_HW_NUM_MAX; i++) { + rc = cam_top_tpg_hw_init(&g_ife_hw_mgr.tpg_devices[i], i); + if (!rc) + j++; + } + if (!j) + CAM_ERR(CAM_ISP, "no valid IFE TPG HW"); + + cam_ife_hw_mgr_sort_dev_with_caps(&g_ife_hw_mgr); /* setup ife context list */ @@ -7146,6 +7237,7 @@ int cam_ife_hw_mgr_init(struct cam_hw_mgr_intf *hw_mgr_intf, int *iommu_hdl) sizeof(g_ife_hw_mgr.ctx_pool[i])); INIT_LIST_HEAD(&g_ife_hw_mgr.ctx_pool[i].list); + INIT_LIST_HEAD(&g_ife_hw_mgr.ctx_pool[i].res_list_tpg.list); INIT_LIST_HEAD(&g_ife_hw_mgr.ctx_pool[i].res_list_ife_in.list); INIT_LIST_HEAD(&g_ife_hw_mgr.ctx_pool[i].res_list_ife_cid); INIT_LIST_HEAD(&g_ife_hw_mgr.ctx_pool[i].res_list_ife_csid); diff --git a/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.h b/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.h index 79033e3458..91caeb314f 100644 --- a/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.h +++ b/drivers/cam_isp/isp_hw_mgr/cam_ife_hw_mgr.h @@ -11,6 +11,7 @@ #include "cam_isp_hw_mgr.h" #include "cam_vfe_hw_intf.h" #include "cam_ife_csid_hw_intf.h" +#include "cam_top_tpg_hw_intf.h" #include "cam_tasklet_util.h" /* IFE resource constants */ @@ -48,6 +49,7 @@ struct cam_ife_hw_mgr_debug { * @slave_hw_idx: hw index for slave core * @hw_mgr: IFE hw mgr which owns this context * @ctx_in_use: flag to tell whether context is active + * @res_list_tpg: TPG resource list * @res_list_ife_in: Starting resource(TPG,PHY0, PHY1...) Can only be * one. * @res_list_csid: CSID resource list @@ -85,6 +87,7 @@ struct cam_ife_hw_mgr_debug { * @custom_enabled update the flag if context is connected to custom HW * @use_frame_header_ts obtain qtimer ts using frame header * @ts captured timestamp when the ctx is acquired + * @is_tpg indicate whether context is using PHY TPG */ struct cam_ife_hw_mgr_ctx { struct list_head list; @@ -97,6 +100,7 @@ struct cam_ife_hw_mgr_ctx { uint32_t ctx_in_use; struct cam_isp_hw_mgr_res res_list_ife_in; + struct cam_isp_hw_mgr_res res_list_tpg; struct list_head res_list_ife_cid; struct list_head res_list_ife_csid; struct list_head res_list_ife_src; @@ -134,6 +138,7 @@ struct cam_ife_hw_mgr_ctx { bool custom_enabled; bool use_frame_header_ts; struct timespec64 ts; + bool is_tpg; }; /** @@ -155,6 +160,7 @@ struct cam_ife_hw_mgr_ctx { */ struct cam_ife_hw_mgr { struct cam_isp_hw_mgr mgr_common; + struct cam_hw_intf *tpg_devices[CAM_TOP_TPG_HW_NUM_MAX]; struct cam_hw_intf *csid_devices[CAM_IFE_CSID_HW_NUM_MAX]; struct cam_hw_intf *ife_devices[CAM_IFE_HW_NUM_MAX]; struct cam_soc_reg_map *cdm_reg_map[CAM_IFE_HW_NUM_MAX]; diff --git a/drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c b/drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c index a3e946e802..fc40510115 100644 --- a/drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c +++ b/drivers/cam_isp/isp_hw_mgr/cam_tfe_hw_mgr.c @@ -1350,7 +1350,7 @@ static int cam_tfe_hw_mgr_acquire_tpg( uint32_t i, j = 0; struct cam_tfe_hw_mgr *tfe_hw_mgr; struct cam_hw_intf *hw_intf; - struct cam_top_tpg_hw_reserve_resource_args tpg_reserve; + struct cam_top_tpg_ver1_reserve_args tpg_reserve; tfe_hw_mgr = tfe_ctx->hw_mgr; diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/ife_csid_hw/cam_ife_csid_core.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/ife_csid_hw/cam_ife_csid_core.c index d2b04752e2..b7787a32ff 100644 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/ife_csid_hw/cam_ife_csid_core.c +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/ife_csid_hw/cam_ife_csid_core.c @@ -25,6 +25,10 @@ #define CAM_IFE_CSID_TPG_VC_VAL 0xA #define CAM_IFE_CSID_TPG_DT_VAL 0x2B +/* CSIPHY TPG VC/DT values */ +#define CAM_IFE_CSI_TPG_VC_VAL 0x0 +#define CAM_IFE_CSI_TPG_DT_VAL 0x2B + /* Timeout values in usec */ #define CAM_IFE_CSID_TIMEOUT_SLEEP_US 1000 #define CAM_IFE_CSID_TIMEOUT_ALL_US 100000 @@ -957,6 +961,12 @@ int cam_ife_csid_cid_reserve(struct cam_ife_csid_hw *csid_hw, csid_hw->tpg_cfg.height); cid_data->tpg_set = 1; + } else if (cid_reserv->in_port->res_type == + CAM_ISP_IFE_IN_RES_CPHY_TPG_0) { + csid_hw->csi2_rx_cfg.phy_sel = 0; + } else if (cid_reserv->in_port->res_type == + CAM_ISP_IFE_IN_RES_CPHY_TPG_1) { + csid_hw->csi2_rx_cfg.phy_sel = 1; } else { csid_hw->csi2_rx_cfg.phy_sel = (cid_reserv->in_port->res_type & 0xFF) - 1; @@ -1129,9 +1139,10 @@ int cam_ife_csid_path_reserve(struct cam_ife_csid_hw *csid_hw, reserve->in_port->line_start, reserve->in_port->line_stop, path_data->crop_enable); - if (reserve->in_port->res_type == CAM_ISP_IFE_IN_RES_TPG) { - path_data->dt = CAM_IFE_CSID_TPG_DT_VAL; - path_data->vc = CAM_IFE_CSID_TPG_VC_VAL; + if ((reserve->in_port->res_type == CAM_ISP_IFE_IN_RES_CPHY_TPG_0) || + (reserve->in_port->res_type == CAM_ISP_IFE_IN_RES_CPHY_TPG_1)) { + path_data->dt = CAM_IFE_CSI_TPG_DT_VAL; + path_data->vc = CAM_IFE_CSI_TPG_VC_VAL; } else { path_data->dt = reserve->in_port->dt[0]; path_data->vc = reserve->in_port->vc[0]; @@ -4459,6 +4470,7 @@ int cam_ife_csid_hw_probe_init(struct cam_hw_intf *csid_hw_intf, num_paths = ife_csid_hw->csid_info->csid_reg->cmn_reg->num_pix + ife_csid_hw->csid_info->csid_reg->cmn_reg->num_rdis + ife_csid_hw->csid_info->csid_reg->cmn_reg->num_udis; + /* Initialize the CID resource */ for (i = 0; i < num_paths; i++) { ife_csid_hw->cid_res[i].res_type = CAM_ISP_RESOURCE_CID; diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_top_tpg_hw_intf.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_top_tpg_hw_intf.h index 17086b50cf..fdbc6639bd 100644 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_top_tpg_hw_intf.h +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/include/cam_top_tpg_hw_intf.h @@ -8,6 +8,7 @@ #include "cam_isp_hw.h" #include "cam_hw_intf.h" +#include "cam_ife_csid_hw_intf.h" /* Max top tpg instance */ #define CAM_TOP_TPG_HW_NUM_MAX 2 @@ -37,7 +38,7 @@ struct cam_top_tpg_hw_caps { }; /** - * struct cam_tfe_csid_hw_reserve_resource_args- hw reserve + * struct cam_top_tpg_ver1_reserve_args- hw reserve * @num_inport: number of inport * TPG support 4 dt types, each different dt comes in different * in port. @@ -45,12 +46,26 @@ struct cam_top_tpg_hw_caps { * @node_res : Reserved resource structure pointer * */ -struct cam_top_tpg_hw_reserve_resource_args { +struct cam_top_tpg_ver1_reserve_args { uint32_t num_inport; struct cam_isp_tfe_in_port_info *in_port[CAM_TOP_TPG_MAX_SUPPORTED_DT]; struct cam_isp_resource_node *node_res; }; +/** + * struct cam_top_tpg_ver2_reserve_args + * @num_inport: number of inport + * TPG supports 1 VC/DT + * @in_port : Input port resource info structure pointer + * @node_res : Reserved resource structure pointer + * + */ +struct cam_top_tpg_ver2_reserve_args { + uint32_t num_inport; + struct cam_isp_in_port_generic_info *in_port; + struct cam_isp_resource_node *node_res; +}; + /** * cam_top_tpg_hw_init() * diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/Makefile b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/Makefile deleted file mode 100644 index f08acab1e1..0000000000 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/Makefile +++ /dev/null @@ -1,15 +0,0 @@ -# SPDX-License-Identifier: GPL-2.0-only - -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_utils -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_core -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_cdm/ -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_cpas/include -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_isp/isp_hw_mgr/include -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_isp/isp_hw_mgr/hw_utils/include -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_isp/isp_hw_mgr/hw_utils/irq_controller -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_isp/isp_hw_mgr/isp_hw/include -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_smmu/ -ccflags-y += -I$(srctree)/techpack/camera/drivers/cam_req_mgr/ - -obj-$(CONFIG_SPECTRA_CAMERA) += cam_top_tpg_dev.o cam_top_tpg_soc.o cam_top_tpg_core.o -obj-$(CONFIG_SPECTRA_CAMERA) += cam_top_tpg_v1.o \ No newline at end of file diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.c new file mode 100644 index 0000000000..9eafcf4da6 --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.c @@ -0,0 +1,48 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. + */ + +#include +#include "cam_top_tpg101.h" +#include "cam_top_tpg102.h" +#include "cam_top_tpg_core.h" +#include "cam_top_tpg_dev.h" +#include "camera_main.h" + +static const struct of_device_id cam_top_tpg_dt_match[] = { + { + .compatible = "qcom,tpg101", + .data = &cam_top_tpg101_hw_info, + }, + { + .compatible = "qcom,tpg102", + .data = &cam_top_tpg102_hw_info, + }, + {} +}; + +MODULE_DEVICE_TABLE(of, cam_top_tpg_dt_match); + +struct platform_driver cam_top_tpg_driver = { + .probe = cam_top_tpg_probe, + .remove = cam_top_tpg_remove, + .driver = { + .name = "cam_top_tpg", + .of_match_table = cam_top_tpg_dt_match, + .suppress_bind_attrs = true, + }, +}; + +int cam_top_tpg_init_module(void) +{ + return platform_driver_register(&cam_top_tpg_driver); +} + +void cam_top_tpg_exit_module(void) +{ + platform_driver_unregister(&cam_top_tpg_driver); +} + +MODULE_DESCRIPTION("CAM TOP TPG driver"); +MODULE_LICENSE("GPL v2"); diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.h new file mode 100644 index 0000000000..6332469056 --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg.h @@ -0,0 +1,12 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +/* + * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. + */ + +#ifndef _CAM_TOP_TPG_H_ +#define _CAM_TOP_TPG_H_ + +int cam_top_tpg_init_module(void); +void cam_top_tpg_exit_module(void); + +#endif /*_CAM_TOP_TPG_H_ */ diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg101.h similarity index 76% rename from drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.h rename to drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg101.h index 2084b811e2..0b99a3f6d1 100644 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.h +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg101.h @@ -3,12 +3,13 @@ * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. */ -#ifndef _CAM_TOP_TPG_V1_H_ -#define _CAM_TOP_TPG_V1_H_ +#ifndef _CAM_TOP_TPG101_H_ +#define _CAM_TOP_TPG101_H_ +#include "cam_top_tpg_ver1.h" #include "cam_top_tpg_core.h" -static struct cam_top_tpg_reg_offset cam_top_tpg_v1_reg_offset = { +static struct cam_top_tpg_ver1_reg_offset cam_top_tpg101_reg = { .tpg_hw_version = 0x0, .tpg_hw_status = 0x4, .tpg_ctrl = 0x60, @@ -50,7 +51,11 @@ static struct cam_top_tpg_reg_offset cam_top_tpg_v1_reg_offset = { .top_mux_reg_offset = 0x1C, }; -int cam_top_tpg_v1_init_module(void); -void cam_top_tpg_v1_exit_module(void); +struct cam_top_tpg_hw_info cam_top_tpg101_hw_info = { + .tpg_reg = &cam_top_tpg101_reg, + .hw_dts_version = CAM_TOP_TPG_VERSION_1, + .csid_max_clk = 426400000, + .phy_max_clk = 384000000, +}; -#endif /*_CAM_TOP_TPG_V1_H_ */ +#endif /* _CAM_TOP_TPG101_H_ */ diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg102.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg102.h new file mode 100644 index 0000000000..ce2f2c73a0 --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg102.h @@ -0,0 +1,50 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +/* + * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. + */ + +#ifndef _CAM_TOP_TPG102_H_ +#define _CAM_TOP_TPG102_H_ + +#include "cam_top_tpg_ver2.h" +#include "cam_top_tpg_core.h" + +static struct cam_top_tpg_ver2_reg_offset cam_top_tpg102_reg = { + .tpg_hw_version = 0x0, + .tpg_hw_status = 0x4, + .tpg_module_cfg = 0x60, + .tpg_cfg_0 = 0x68, + .tpg_cfg_1 = 0x6C, + .tpg_cfg_2 = 0x70, + .tpg_cfg_3 = 0x74, + .tpg_spare = 0xFC, + .top_mux_sel = 0x90, + /* configurations */ + .major_version = 1, + .minor_version = 0, + .version_incr = 0, + .tpg_module_en = 1, + .tpg_mux_sel_en = 1, + .tpg_mux_sel_tpg_0_shift = 0, + .tpg_mux_sel_tpg_1_shift = 8, + .tpg_en_shift_val = 0, + .tpg_phy_sel_shift_val = 3, + .tpg_num_active_lines_shift = 4, + .tpg_fe_pkt_en_shift = 2, + .tpg_fs_pkt_en_shift = 1, + .tpg_line_interleaving_mode_shift = 10, + .tpg_num_dts_shift_val = 8, + .tpg_v_blank_cnt_shift = 12, + .tpg_dt_encode_format_shift = 16, + .tpg_payload_mode_color = 0x8, + .tpg_split_en_shift = 5, +}; + +struct cam_top_tpg_hw_info cam_top_tpg102_hw_info = { + .tpg_reg = &cam_top_tpg102_reg, + .hw_dts_version = CAM_TOP_TPG_VERSION_2, + .csid_max_clk = 426400000, + .phy_max_clk = 384000000, +}; + +#endif /* _CAM_TOP_TPG102_H_ */ diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.c index 6a544faf54..64b776623d 100644 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.c +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.c @@ -13,210 +13,8 @@ #include "cam_io_util.h" #include "cam_debug_util.h" #include "cam_cpas_api.h" - - -static uint32_t tpg_num_dt_map[CAM_TOP_TPG_MAX_SUPPORTED_DT] = { - 0, - 3, - 1, - 2 -}; - -static int cam_top_tpg_get_format(uint32_t in_format, - uint32_t *tpg_encode_format) -{ - int rc = 0; - - switch (in_format) { - case CAM_FORMAT_MIPI_RAW_6: - *tpg_encode_format = 0; - break; - case CAM_FORMAT_MIPI_RAW_8: - *tpg_encode_format = 1; - break; - case CAM_FORMAT_MIPI_RAW_10: - *tpg_encode_format = 2; - break; - case CAM_FORMAT_MIPI_RAW_12: - *tpg_encode_format = 3; - break; - case CAM_FORMAT_MIPI_RAW_14: - *tpg_encode_format = 4; - break; - case CAM_FORMAT_MIPI_RAW_16: - *tpg_encode_format = 4; - break; - default: - CAM_ERR(CAM_ISP, "Unsupported input encode format %d", - in_format); - rc = -EINVAL; - } - return rc; -} - -static int cam_top_tpg_get_hw_caps(void *hw_priv, - void *get_hw_cap_args, uint32_t arg_size) -{ - int rc = 0; - struct cam_top_tpg_hw_caps *hw_caps; - struct cam_top_tpg_hw *tpg_hw; - struct cam_hw_info *tpg_hw_info; - - if (!hw_priv || !get_hw_cap_args) { - CAM_ERR(CAM_ISP, "TPG: Invalid args"); - return -EINVAL; - } - - tpg_hw_info = (struct cam_hw_info *)hw_priv; - tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; - hw_caps = (struct cam_top_tpg_hw_caps *) get_hw_cap_args; - - hw_caps->major_version = tpg_hw->tpg_info->tpg_reg->major_version; - hw_caps->minor_version = tpg_hw->tpg_info->tpg_reg->minor_version; - hw_caps->version_incr = tpg_hw->tpg_info->tpg_reg->version_incr; - - CAM_DBG(CAM_ISP, - "TPG:%d major:%d minor:%d ver :%d", - tpg_hw->hw_intf->hw_idx, hw_caps->major_version, - hw_caps->minor_version, hw_caps->version_incr); - - return rc; -} - -static int cam_top_tpg_reserve(void *hw_priv, - void *reserve_args, uint32_t arg_size) -{ - int rc = 0; - struct cam_top_tpg_hw *tpg_hw; - struct cam_hw_info *tpg_hw_info; - struct cam_top_tpg_hw_reserve_resource_args *reserv; - struct cam_top_tpg_cfg *tpg_data; - uint32_t encode_format = 0; - uint32_t i; - - if (!hw_priv || !reserve_args || (arg_size != - sizeof(struct cam_top_tpg_hw_reserve_resource_args))) { - CAM_ERR(CAM_ISP, "TPG: Invalid args"); - return -EINVAL; - } - - tpg_hw_info = (struct cam_hw_info *)hw_priv; - tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; - reserv = (struct cam_top_tpg_hw_reserve_resource_args *)reserve_args; - - if (reserv->num_inport <= 0 || - reserv->num_inport > CAM_TOP_TPG_MAX_SUPPORTED_DT) { - CAM_ERR_RATE_LIMIT(CAM_ISP, "TPG: %u invalid input num port:%d", - tpg_hw->hw_intf->hw_idx, reserv->num_inport); - return -EINVAL; - } - - mutex_lock(&tpg_hw->hw_info->hw_mutex); - if (tpg_hw->tpg_res.res_state != CAM_ISP_RESOURCE_STATE_AVAILABLE) { - mutex_unlock(&tpg_hw->hw_info->hw_mutex); - return -EINVAL; - } - - if ((reserv->in_port[0]->vc > 0xF) || - (reserv->in_port[0]->lane_num <= 0 || - reserv->in_port[0]->lane_num > 4) || - (reserv->in_port[0]->pix_pattern > 4) || - (reserv->in_port[0]->lane_type >= 2)) { - CAM_ERR_RATE_LIMIT(CAM_ISP, "TPG:%u invalid input %d %d %d %d", - tpg_hw->hw_intf->hw_idx, reserv->in_port[0]->vc, - reserv->in_port[0]->lane_num, - reserv->in_port[0]->pix_pattern, - reserv->in_port[0]->lane_type); - mutex_unlock(&tpg_hw->hw_info->hw_mutex); - return -EINVAL; - } - rc = cam_top_tpg_get_format(reserv->in_port[0]->format, - &encode_format); - if (rc) - goto error; - - CAM_DBG(CAM_ISP, "TPG: %u enter", tpg_hw->hw_intf->hw_idx); - - tpg_data = (struct cam_top_tpg_cfg *)tpg_hw->tpg_res.res_priv; - tpg_data->vc_num = reserv->in_port[0]->vc; - tpg_data->phy_sel = reserv->in_port[0]->lane_type; - tpg_data->num_active_lanes = reserv->in_port[0]->lane_num; - tpg_data->h_blank_count = reserv->in_port[0]->sensor_hbi; - tpg_data->v_blank_count = reserv->in_port[0]->sensor_vbi; - tpg_data->pix_pattern = reserv->in_port[0]->pix_pattern; - tpg_data->dt_cfg[0].data_type = reserv->in_port[0]->dt; - tpg_data->dt_cfg[0].frame_height = reserv->in_port[0]->height; - if (reserv->in_port[0]->usage_type) - tpg_data->dt_cfg[0].frame_width = - ((reserv->in_port[0]->right_end - - reserv->in_port[0]->left_start) + 1); - else - tpg_data->dt_cfg[0].frame_width = - reserv->in_port[0]->left_width; - tpg_data->dt_cfg[0].encode_format = encode_format; - tpg_data->num_active_dts = 1; - - CAM_DBG(CAM_ISP, - "TPG:%u vc_num:%d dt:%d phy:%d lines:%d pattern:%d format:%d", - tpg_hw->hw_intf->hw_idx, - tpg_data->vc_num, tpg_data->dt_cfg[0].data_type, - tpg_data->phy_sel, tpg_data->num_active_lanes, - tpg_data->pix_pattern, - tpg_data->dt_cfg[0].encode_format); - - CAM_DBG(CAM_ISP, "TPG:%u height:%d width:%d h blank:%d v blank:%d", - tpg_hw->hw_intf->hw_idx, - tpg_data->dt_cfg[0].frame_height, - tpg_data->dt_cfg[0].frame_width, - tpg_data->h_blank_count, - tpg_data->v_blank_count); - - if (reserv->num_inport == 1) - goto end; - - for (i = 1; i < reserv->num_inport; i++) { - if ((tpg_data->vc_num != reserv->in_port[i]->vc) || - (tpg_data->phy_sel != reserv->in_port[i]->lane_type) || - (tpg_data->num_active_lanes != - reserv->in_port[i]->lane_num) || - (tpg_data->pix_pattern != - reserv->in_port[i]->pix_pattern)) { - CAM_ERR_RATE_LIMIT(CAM_ISP, - "TPG: %u invalid DT config for tpg", - tpg_hw->hw_intf->hw_idx); - rc = -EINVAL; - goto error; - } - rc = cam_top_tpg_get_format(reserv->in_port[0]->format, - &encode_format); - if (rc) - return rc; - - tpg_data->dt_cfg[i].data_type = reserv->in_port[i]->dt; - tpg_data->dt_cfg[i].frame_height = - reserv->in_port[i]->height; - tpg_data->dt_cfg[i].frame_width = - reserv->in_port[i]->left_width; - tpg_data->dt_cfg[i].encode_format = encode_format; - tpg_data->num_active_dts++; - - CAM_DBG(CAM_ISP, "TPG:%u height:%d width:%d dt:%d format:%d", - tpg_hw->hw_intf->hw_idx, - tpg_data->dt_cfg[i].frame_height, - tpg_data->dt_cfg[i].frame_width, - tpg_data->dt_cfg[i].data_type, - tpg_data->dt_cfg[i].encode_format); - - } -end: - reserv->node_res = &tpg_hw->tpg_res; - tpg_hw->tpg_res.res_state = CAM_ISP_RESOURCE_STATE_RESERVED; -error: - mutex_unlock(&tpg_hw->hw_info->hw_mutex); - CAM_DBG(CAM_ISP, "exit rc %u", rc); - - return rc; -} +#include "cam_top_tpg_ver1.h" +#include "cam_top_tpg_ver2.h" static int cam_top_tpg_release(void *hw_priv, void *release_args, uint32_t arg_size) @@ -266,9 +64,8 @@ static int cam_top_tpg_init_hw(void *hw_priv, struct cam_top_tpg_hw *tpg_hw; struct cam_hw_info *tpg_hw_info; struct cam_isp_resource_node *tpg_res; - const struct cam_top_tpg_reg_offset *tpg_reg; struct cam_hw_soc_info *soc_info; - uint32_t val, clk_lvl; + uint32_t clk_lvl; if (!hw_priv || !init_args || (arg_size != sizeof(struct cam_isp_resource_node))) { @@ -278,8 +75,7 @@ static int cam_top_tpg_init_hw(void *hw_priv, tpg_hw_info = (struct cam_hw_info *)hw_priv; tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; - tpg_res = (struct cam_isp_resource_node *)init_args; - tpg_reg = tpg_hw->tpg_info->tpg_reg; + tpg_res = (struct cam_isp_resource_node *)init_args; soc_info = &tpg_hw->hw_info->soc_info; if (tpg_res->res_type != CAM_ISP_RESOURCE_TPG) { @@ -321,11 +117,6 @@ static int cam_top_tpg_init_hw(void *hw_priv, tpg_hw->hw_info->hw_state = CAM_HW_STATE_POWER_UP; - val = cam_io_r_mb(soc_info->reg_map[0].mem_base + - tpg_reg->tpg_hw_version); - CAM_DBG(CAM_ISP, "TPG:%d TPG HW version: 0x%x", - tpg_hw->hw_intf->hw_idx, val); - mutex_unlock(&tpg_hw->hw_info->hw_mutex); return rc; @@ -389,148 +180,6 @@ end: return rc; } -static int cam_top_tpg_start(void *hw_priv, void *start_args, - uint32_t arg_size) -{ - int rc = 0; - struct cam_top_tpg_hw *tpg_hw; - struct cam_hw_info *tpg_hw_info; - struct cam_hw_soc_info *soc_info; - struct cam_isp_resource_node *tpg_res; - const struct cam_top_tpg_reg_offset *tpg_reg; - struct cam_top_tpg_cfg *tpg_data; - uint32_t i, val; - - if (!hw_priv || !start_args || - (arg_size != sizeof(struct cam_isp_resource_node))) { - CAM_ERR(CAM_ISP, "TPG: Invalid args"); - return -EINVAL; - } - - tpg_hw_info = (struct cam_hw_info *)hw_priv; - tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; - tpg_reg = tpg_hw->tpg_info->tpg_reg; - tpg_res = (struct cam_isp_resource_node *)start_args; - tpg_data = (struct cam_top_tpg_cfg *)tpg_res->res_priv; - soc_info = &tpg_hw->hw_info->soc_info; - - if ((tpg_res->res_type != CAM_ISP_RESOURCE_TPG) || - (tpg_res->res_state != CAM_ISP_RESOURCE_STATE_RESERVED)) { - CAM_ERR(CAM_ISP, "TPG:%d Invalid Res type:%d res_state:%d", - tpg_hw->hw_intf->hw_idx, - tpg_res->res_type, tpg_res->res_state); - rc = -EINVAL; - goto end; - } - cam_io_w_mb(0x12345678, soc_info->reg_map[0].mem_base + - tpg_reg->tpg_lfsr_seed); - - for (i = 0; i < tpg_data->num_active_dts; i++) { - val = (((tpg_data->dt_cfg[i].frame_width & 0xFFFF) << 16) | - (tpg_data->dt_cfg[i].frame_height & 0x3FFF)); - cam_io_w_mb(val, soc_info->reg_map[0].mem_base + - tpg_reg->tpg_dt_0_cfg_0 + 0x10 * i); - cam_io_w_mb(tpg_data->dt_cfg[i].data_type, - soc_info->reg_map[0].mem_base + - tpg_reg->tpg_dt_0_cfg_1 + 0x10 * i); - val = ((tpg_data->dt_cfg[i].encode_format & 0xF) << - tpg_reg->tpg_dt_encode_format_shift) | - tpg_reg->tpg_payload_mode_color; - cam_io_w_mb(val, soc_info->reg_map[0].mem_base + - tpg_reg->tpg_dt_0_cfg_2 + 0x10 * i); - } - - val = (tpg_num_dt_map[tpg_data->num_active_dts-1] << - tpg_reg->tpg_num_dts_shift_val) | tpg_data->vc_num; - cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_vc_cfg0); - - /* - * if hblank is notset configureHBlank count 500 and - * V blank count is 600 - */ - - if (tpg_data->h_blank_count) - cam_io_w_mb(tpg_data->h_blank_count, - soc_info->reg_map[0].mem_base + tpg_reg->tpg_vc_cfg1); - else - cam_io_w_mb(0x2581F4, - soc_info->reg_map[0].mem_base + tpg_reg->tpg_vc_cfg1); - - val = (1 << tpg_reg->tpg_split_en_shift); - cam_io_w_mb(tpg_data->pix_pattern, soc_info->reg_map[0].mem_base + - tpg_reg->tpg_common_gen_cfg); - - /* if VBI is notset configureVBI to 0xAFF */ - if (tpg_data->v_blank_count) - cam_io_w_mb(tpg_data->v_blank_count, - soc_info->reg_map[0].mem_base + tpg_reg->tpg_vbi_cfg); - else - cam_io_w_mb(0xAFFF, - soc_info->reg_map[0].mem_base + tpg_reg->tpg_vbi_cfg); - - /* Set the TOP tpg mux sel*/ - cam_io_w_mb((1 << tpg_hw->hw_intf->hw_idx), - soc_info->reg_map[1].mem_base + tpg_reg->top_mux_reg_offset); - - val = ((tpg_data->num_active_lanes - 1) << - tpg_reg->tpg_num_active_lines_shift) | - (1 << tpg_reg->tpg_fe_pkt_en_shift) | - (1 << tpg_reg->tpg_fs_pkt_en_shift) | - (tpg_data->phy_sel << tpg_reg->tpg_phy_sel_shift_val) | - (1 << tpg_reg->tpg_en_shift_val); - cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_ctrl); - - tpg_res->res_state = CAM_ISP_RESOURCE_STATE_STREAMING; - - CAM_DBG(CAM_ISP, "TPG:%d started", tpg_hw->hw_intf->hw_idx); - -end: - return rc; -} - -static int cam_top_tpg_stop(void *hw_priv, - void *stop_args, uint32_t arg_size) -{ - int rc = 0; - struct cam_top_tpg_hw *tpg_hw; - struct cam_hw_info *tpg_hw_info; - struct cam_hw_soc_info *soc_info; - struct cam_isp_resource_node *tpg_res; - const struct cam_top_tpg_reg_offset *tpg_reg; - struct cam_top_tpg_cfg *tpg_data; - - if (!hw_priv || !stop_args || - (arg_size != sizeof(struct cam_isp_resource_node))) { - CAM_ERR(CAM_ISP, "TPG: Invalid args"); - return -EINVAL; - } - - tpg_hw_info = (struct cam_hw_info *)hw_priv; - tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; - tpg_reg = tpg_hw->tpg_info->tpg_reg; - tpg_res = (struct cam_isp_resource_node *) stop_args; - tpg_data = (struct cam_top_tpg_cfg *)tpg_res->res_state; - soc_info = &tpg_hw->hw_info->soc_info; - - if ((tpg_res->res_type != CAM_ISP_RESOURCE_TPG) || - (tpg_res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING)) { - CAM_DBG(CAM_ISP, "TPG:%d Invalid Res type:%d res_state:%d", - tpg_hw->hw_intf->hw_idx, - tpg_res->res_type, tpg_res->res_state); - rc = -EINVAL; - goto end; - } - - cam_io_w_mb(0, soc_info->reg_map[0].mem_base + - tpg_reg->tpg_ctrl); - - tpg_res->res_state = CAM_ISP_RESOURCE_STATE_RESERVED; - - CAM_DBG(CAM_ISP, "TPG:%d stopped", tpg_hw->hw_intf->hw_idx); -end: - return rc; -} - static int cam_top_tpg_read(void *hw_priv, void *read_args, uint32_t arg_size) { @@ -592,14 +241,14 @@ static int cam_top_tpg_process_cmd(void *hw_priv, return 0; } -int cam_top_tpg_hw_probe_init(struct cam_hw_intf *tpg_hw_intf, +int cam_top_tpg_probe_init(struct cam_hw_intf *tpg_hw_intf, uint32_t tpg_idx) { int rc = -EINVAL; struct cam_top_tpg_cfg *tpg_data; struct cam_hw_info *tpg_hw_info; struct cam_top_tpg_hw *tpg_hw = NULL; - uint32_t val = 0; + uint32_t hw_version = 0; if (tpg_idx >= CAM_TOP_TPG_HW_NUM_MAX) { CAM_ERR(CAM_ISP, "Invalid tpg index:%d", tpg_idx); @@ -620,7 +269,6 @@ int cam_top_tpg_hw_probe_init(struct cam_hw_intf *tpg_hw_intf, spin_lock_init(&tpg_hw->hw_info->hw_lock); spin_lock_init(&tpg_hw->lock_state); init_completion(&tpg_hw->hw_info->hw_complete); - init_completion(&tpg_hw->tpg_complete); rc = cam_top_tpg_init_soc_resources(&tpg_hw->hw_info->soc_info, @@ -630,18 +278,20 @@ int cam_top_tpg_hw_probe_init(struct cam_hw_intf *tpg_hw_intf, goto err; } - tpg_hw->hw_intf->hw_ops.get_hw_caps = cam_top_tpg_get_hw_caps; tpg_hw->hw_intf->hw_ops.init = cam_top_tpg_init_hw; tpg_hw->hw_intf->hw_ops.deinit = cam_top_tpg_deinit_hw; tpg_hw->hw_intf->hw_ops.reset = NULL; - tpg_hw->hw_intf->hw_ops.reserve = cam_top_tpg_reserve; tpg_hw->hw_intf->hw_ops.release = cam_top_tpg_release; - tpg_hw->hw_intf->hw_ops.start = cam_top_tpg_start; - tpg_hw->hw_intf->hw_ops.stop = cam_top_tpg_stop; tpg_hw->hw_intf->hw_ops.read = cam_top_tpg_read; tpg_hw->hw_intf->hw_ops.write = cam_top_tpg_write; tpg_hw->hw_intf->hw_ops.process_cmd = cam_top_tpg_process_cmd; + hw_version = tpg_hw->tpg_info->hw_dts_version; + if (hw_version == CAM_TOP_TPG_VERSION_1) + cam_top_tpg_ver1_init(tpg_hw); + else if (hw_version == CAM_TOP_TPG_VERSION_2) + cam_top_tpg_ver2_init(tpg_hw); + tpg_hw->tpg_res.res_type = CAM_ISP_RESOURCE_TPG; tpg_hw->tpg_res.res_state = CAM_ISP_RESOURCE_STATE_AVAILABLE; tpg_hw->tpg_res.hw_intf = tpg_hw->hw_intf; @@ -655,18 +305,13 @@ int cam_top_tpg_hw_probe_init(struct cam_hw_intf *tpg_hw_intf, cam_top_tpg_enable_soc_resources(&tpg_hw->hw_info->soc_info, CAM_SVS_VOTE); - val = cam_io_r_mb(tpg_hw->hw_info->soc_info.reg_map[0].mem_base + - tpg_hw->tpg_info->tpg_reg->tpg_hw_version); - CAM_DBG(CAM_ISP, "TPG:%d TPG HW version: 0x%x", - tpg_hw->hw_intf->hw_idx, val); - cam_top_tpg_disable_soc_resources(&tpg_hw->hw_info->soc_info); -err: +err: return rc; } -int cam_top_tpg_hw_deinit(struct cam_top_tpg_hw *top_tpg_hw) +int cam_top_tpg_deinit(struct cam_top_tpg_hw *top_tpg_hw) { int rc = -EINVAL; diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.h index 12f7cfc85e..3dce37d94f 100644 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.h +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_core.h @@ -3,13 +3,16 @@ * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. */ -#ifndef _CAM_TOP_TPG_HW_H_ -#define _CAM_TOP_TPG_HW_H_ +#ifndef _CAM_TOP_TPG_CORE_H_ +#define _CAM_TOP_TPG_CORE_H_ #include "cam_hw.h" #include "cam_top_tpg_hw_intf.h" #include "cam_top_tpg_soc.h" +#define CAM_TOP_TPG_VERSION_1 0x10000001 +#define CAM_TOP_TPG_VERSION_2 0x10000002 + enum cam_top_tpg_encode_format { CAM_TOP_TPG_ENCODE_FORMAT_RAW6, CAM_TOP_TPG_ENCODE_FORMAT_RAW8, @@ -20,48 +23,6 @@ enum cam_top_tpg_encode_format { CAM_TOP_TPG_ENCODE_FORMAT_MAX, }; -struct cam_top_tpg_reg_offset { - uint32_t tpg_hw_version; - uint32_t tpg_hw_status; - uint32_t tpg_ctrl; - uint32_t tpg_vc_cfg0; - uint32_t tpg_vc_cfg1; - uint32_t tpg_lfsr_seed; - uint32_t tpg_dt_0_cfg_0; - uint32_t tpg_dt_1_cfg_0; - uint32_t tpg_dt_2_cfg_0; - uint32_t tpg_dt_3_cfg_0; - uint32_t tpg_dt_0_cfg_1; - uint32_t tpg_dt_1_cfg_1; - uint32_t tpg_dt_2_cfg_1; - uint32_t tpg_dt_3_cfg_1; - uint32_t tpg_dt_0_cfg_2; - uint32_t tpg_dt_1_cfg_2; - uint32_t tpg_dt_2_cfg_2; - uint32_t tpg_dt_3_cfg_2; - uint32_t tpg_color_bar_cfg; - uint32_t tpg_common_gen_cfg; - uint32_t tpg_vbi_cfg; - uint32_t tpg_test_bus_crtl; - uint32_t tpg_spare; - /* configurations */ - uint32_t major_version; - uint32_t minor_version; - uint32_t version_incr; - uint32_t tpg_en_shift_val; - uint32_t tpg_phy_sel_shift_val; - uint32_t tpg_num_active_lines_shift; - uint32_t tpg_fe_pkt_en_shift; - uint32_t tpg_fs_pkt_en_shift; - uint32_t tpg_line_interleaving_mode_shift; - uint32_t tpg_num_dts_shift_val; - uint32_t tpg_v_blank_cnt_shift; - uint32_t tpg_dt_encode_format_shift; - uint32_t tpg_payload_mode_color; - uint32_t tpg_split_en_shift; - uint32_t top_mux_reg_offset; -}; - /** * struct cam_top_tpg_hw_info- tpg hardware info * @@ -72,7 +33,7 @@ struct cam_top_tpg_reg_offset { * */ struct cam_top_tpg_hw_info { - const struct cam_top_tpg_reg_offset *tpg_reg; + void *tpg_reg; uint32_t hw_dts_version; uint32_t csid_max_clk; uint32_t phy_max_clk; @@ -86,15 +47,24 @@ struct cam_top_tpg_hw_info { * @data_type: data type(dt) value * @encode_format: encode format for this data type * @payload_mode payload data, such color bar, color box etc + * @bayer_pattern: Bayer patter information + * @rotate_period: period value for repeating color, 0 for no rotate + * @split_en: enables split mode + * @unicolor_en: enables unicolor value + * @unicolor_sel: select color used in unicolor mode * */ - struct cam_top_tpg_dt_cfg { uint32_t frame_width; uint32_t frame_height; uint32_t data_type; uint32_t encode_format; uint32_t payload_mode; + uint32_t bayer_pattern; + uint32_t rotate_period; + uint32_t split_en; + uint32_t unicolor_en; + uint32_t unicolor_sel; }; /** @@ -107,6 +77,7 @@ struct cam_top_tpg_dt_cfg { * @h_blank_count: vertical blanking count value * @vbi_cnt: vbi count * @num_active_dts: number of active dts need to configure + * @num_frames: number of output frames * @dt_cfg: dt configuration values * */ @@ -119,6 +90,7 @@ struct cam_top_tpg_cfg { uint32_t h_blank_count; uint32_t vbi_cnt; uint32_t num_active_dts; + uint32_t num_frames; struct cam_top_tpg_dt_cfg dt_cfg[4]; }; @@ -145,9 +117,9 @@ struct cam_top_tpg_hw { struct completion tpg_complete; }; -int cam_top_tpg_hw_probe_init(struct cam_hw_intf *tpg_hw_intf, +int cam_top_tpg_probe_init(struct cam_hw_intf *tpg_hw_intf, uint32_t tpg_idx); -int cam_top_tpg_hw_deinit(struct cam_top_tpg_hw *top_tpg_hw); +int cam_top_tpg_deinit(struct cam_top_tpg_hw *top_tpg_hw); -#endif /* _CAM_TOP_TPG_HW_H_ */ +#endif /* _CAM_TOP_TPG_CORE_H_ */ diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_dev.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_dev.c index ebb355a29d..fa4828c5bc 100644 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_dev.c +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_dev.c @@ -21,10 +21,10 @@ static int cam_top_tpg_component_bind(struct device *dev, struct device *master_dev, void *data) { struct cam_hw_intf *tpg_hw_intf; - struct cam_hw_info *tpg_hw_info; - struct cam_top_tpg_hw *tpg_dev = NULL; + struct cam_hw_info *hw_info; + struct cam_top_tpg_hw *tpg_hw = NULL; const struct of_device_id *match_dev = NULL; - struct cam_top_tpg_hw_info *tpg_hw_data = NULL; + struct cam_top_tpg_hw_info *tpg_hw_info = NULL; uint32_t tpg_dev_idx; int rc = 0; struct platform_device *pdev = to_platform_device(dev); @@ -37,14 +37,14 @@ static int cam_top_tpg_component_bind(struct device *dev, goto err; } - tpg_hw_info = kzalloc(sizeof(struct cam_hw_info), GFP_KERNEL); - if (!tpg_hw_info) { + hw_info = kzalloc(sizeof(struct cam_hw_info), GFP_KERNEL); + if (!hw_info) { rc = -ENOMEM; goto free_hw_intf; } - tpg_dev = kzalloc(sizeof(struct cam_top_tpg_hw), GFP_KERNEL); - if (!tpg_dev) { + tpg_hw = kzalloc(sizeof(struct cam_top_tpg_hw), GFP_KERNEL); + if (!tpg_hw) { rc = -ENOMEM; goto free_hw_info; } @@ -66,23 +66,23 @@ static int cam_top_tpg_component_bind(struct device *dev, tpg_hw_intf->hw_idx = tpg_dev_idx; tpg_hw_intf->hw_type = CAM_ISP_HW_TYPE_TPG; - tpg_hw_intf->hw_priv = tpg_hw_info; + tpg_hw_intf->hw_priv = hw_info; - tpg_hw_info->core_info = tpg_dev; - tpg_hw_info->soc_info.pdev = pdev; - tpg_hw_info->soc_info.dev = &pdev->dev; - tpg_hw_info->soc_info.dev_name = tpg_dev_name; - tpg_hw_info->soc_info.index = tpg_dev_idx; + hw_info->core_info = tpg_hw; + hw_info->soc_info.pdev = pdev; + hw_info->soc_info.dev = &pdev->dev; + hw_info->soc_info.dev_name = tpg_dev_name; + hw_info->soc_info.index = tpg_dev_idx; - tpg_hw_data = (struct cam_top_tpg_hw_info *)match_dev->data; + tpg_hw_info = (struct cam_top_tpg_hw_info *)match_dev->data; /* need to setup the pdev before call the tfe hw probe init */ - tpg_dev->tpg_info = tpg_hw_data; + tpg_hw->tpg_info = tpg_hw_info; - rc = cam_top_tpg_hw_probe_init(tpg_hw_intf, tpg_dev_idx); + rc = cam_top_tpg_probe_init(tpg_hw_intf, tpg_dev_idx); if (rc) goto free_dev; - platform_set_drvdata(pdev, tpg_dev); + platform_set_drvdata(pdev, tpg_hw); CAM_DBG(CAM_ISP, "TPG: %d component binded successfully", tpg_hw_intf->hw_idx); @@ -94,9 +94,9 @@ static int cam_top_tpg_component_bind(struct device *dev, return 0; free_dev: - kfree(tpg_dev); + kfree(tpg_hw); free_hw_info: - kfree(tpg_hw_info); + kfree(hw_info); free_hw_intf: kfree(tpg_hw_intf); err: @@ -108,19 +108,19 @@ static void cam_top_tpg_component_unbind(struct device *dev, { struct cam_top_tpg_hw *tpg_dev = NULL; struct cam_hw_intf *tpg_hw_intf; - struct cam_hw_info *tpg_hw_info; struct platform_device *pdev = to_platform_device(dev); + struct cam_hw_info *hw_info; tpg_dev = (struct cam_top_tpg_hw *)platform_get_drvdata(pdev); tpg_hw_intf = tpg_dev->hw_intf; - tpg_hw_info = tpg_dev->hw_info; + hw_info = tpg_dev->hw_info; CAM_DBG(CAM_ISP, "TPG:%d component unbound", tpg_dev->hw_intf->hw_idx); - cam_top_tpg_hw_deinit(tpg_dev); + cam_top_tpg_deinit(tpg_dev); /*release the tpg device memory */ kfree(tpg_dev); - kfree(tpg_hw_info); + kfree(hw_info); kfree(tpg_hw_intf); } diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.c deleted file mode 100644 index 8564a30339..0000000000 --- a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_v1.c +++ /dev/null @@ -1,54 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0-only -/* - * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. - */ - - -#include -#include "cam_top_tpg_core.h" -#include "cam_top_tpg_v1.h" -#include "cam_top_tpg_dev.h" -#include "camera_main.h" - -#define CAM_TOP_TPG_DRV_NAME "tpg_v1" -#define CAM_TOP_TPG_VERSION_V1 0x10000000 - -static struct cam_top_tpg_hw_info cam_top_tpg_v1_hw_info = { - .tpg_reg = &cam_top_tpg_v1_reg_offset, - .hw_dts_version = CAM_TOP_TPG_VERSION_V1, - .csid_max_clk = 426400000, - .phy_max_clk = 384000000, -}; - -static const struct of_device_id cam_top_tpg_v1_dt_match[] = { - { - .compatible = "qcom,tpgv1", - .data = &cam_top_tpg_v1_hw_info, - }, - {} -}; - -MODULE_DEVICE_TABLE(of, cam_top_tpg_v1_dt_match); - -struct platform_driver cam_top_tpg_v1_driver = { - .probe = cam_top_tpg_probe, - .remove = cam_top_tpg_remove, - .driver = { - .name = CAM_TOP_TPG_DRV_NAME, - .of_match_table = cam_top_tpg_v1_dt_match, - .suppress_bind_attrs = true, - }, -}; - -int cam_top_tpg_v1_init_module(void) -{ - return platform_driver_register(&cam_top_tpg_v1_driver); -} - -void cam_top_tpg_v1_exit_module(void) -{ - platform_driver_unregister(&cam_top_tpg_v1_driver); -} - -MODULE_DESCRIPTION("CAM TOP TPG driver"); -MODULE_LICENSE("GPL v2"); diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.c new file mode 100644 index 0000000000..24c930f125 --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.c @@ -0,0 +1,385 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (c) 2020, The Linux Foundation. All rights reserved. + */ + +#include +#include +#include +#include + +#include "cam_top_tpg_core.h" +#include "cam_soc_util.h" +#include "cam_io_util.h" +#include "cam_debug_util.h" +#include "cam_top_tpg_ver1.h" + +static uint32_t tpg_num_dt_map[CAM_TOP_TPG_MAX_SUPPORTED_DT] = { + 0, + 3, + 1, + 2 +}; + +static int cam_top_tpg_ver1_get_format( + uint32_t in_format, + uint32_t *tpg_encode_format) +{ + int rc = 0; + + switch (in_format) { + case CAM_FORMAT_MIPI_RAW_6: + *tpg_encode_format = 0; + break; + case CAM_FORMAT_MIPI_RAW_8: + *tpg_encode_format = 1; + break; + case CAM_FORMAT_MIPI_RAW_10: + *tpg_encode_format = 2; + break; + case CAM_FORMAT_MIPI_RAW_12: + *tpg_encode_format = 3; + break; + case CAM_FORMAT_MIPI_RAW_14: + *tpg_encode_format = 4; + break; + case CAM_FORMAT_MIPI_RAW_16: + *tpg_encode_format = 4; + break; + default: + CAM_ERR(CAM_ISP, "Unsupported input encode format %d", + in_format); + rc = -EINVAL; + } + return rc; +} + +static int cam_top_tpg_ver1_get_hw_caps( + void *hw_priv, + void *get_hw_cap_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw_caps *hw_caps; + struct cam_top_tpg_hw *tpg_hw; + const struct cam_top_tpg_ver1_reg_offset *tpg_reg; + struct cam_hw_info *tpg_hw_info; + + if (!hw_priv || !get_hw_cap_args) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + hw_caps = (struct cam_top_tpg_hw_caps *) get_hw_cap_args; + tpg_reg = tpg_hw->tpg_info->tpg_reg; + + hw_caps->major_version = tpg_reg->major_version; + hw_caps->minor_version = tpg_reg->minor_version; + hw_caps->version_incr = tpg_reg->version_incr; + + CAM_DBG(CAM_ISP, + "TPG:%d major:%d minor:%d ver :%d", + tpg_hw->hw_intf->hw_idx, hw_caps->major_version, + hw_caps->minor_version, hw_caps->version_incr); + + return rc; +} + +static int cam_top_tpg_ver1_reserve( + void *hw_priv, + void *reserve_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw *tpg_hw; + struct cam_hw_info *tpg_hw_info; + struct cam_top_tpg_ver1_reserve_args *reserv; + struct cam_top_tpg_cfg *tpg_data; + uint32_t encode_format = 0; + uint32_t i; + + if (!hw_priv || !reserve_args || (arg_size != + sizeof(struct cam_top_tpg_ver1_reserve_args))) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + reserv = (struct cam_top_tpg_ver1_reserve_args *)reserve_args; + + if (reserv->num_inport <= 0 || + reserv->num_inport > CAM_TOP_TPG_MAX_SUPPORTED_DT) { + CAM_ERR_RATE_LIMIT(CAM_ISP, "TPG: %u invalid input num port:%d", + tpg_hw->hw_intf->hw_idx, reserv->num_inport); + return -EINVAL; + } + + mutex_lock(&tpg_hw->hw_info->hw_mutex); + if (tpg_hw->tpg_res.res_state != CAM_ISP_RESOURCE_STATE_AVAILABLE) { + mutex_unlock(&tpg_hw->hw_info->hw_mutex); + return -EINVAL; + } + + if ((reserv->in_port[0]->vc > 0xF) || + (reserv->in_port[0]->lane_num <= 0 || + reserv->in_port[0]->lane_num > 4) || + (reserv->in_port[0]->pix_pattern > 4) || + (reserv->in_port[0]->lane_type >= 2)) { + CAM_ERR_RATE_LIMIT(CAM_ISP, "TPG:%u invalid input %d %d %d %d", + tpg_hw->hw_intf->hw_idx, reserv->in_port[0]->vc, + reserv->in_port[0]->lane_num, + reserv->in_port[0]->pix_pattern, + reserv->in_port[0]->lane_type); + mutex_unlock(&tpg_hw->hw_info->hw_mutex); + return -EINVAL; + } + rc = cam_top_tpg_ver1_get_format(reserv->in_port[0]->format, + &encode_format); + if (rc) + goto error; + + CAM_DBG(CAM_ISP, "TPG: %u enter", tpg_hw->hw_intf->hw_idx); + + tpg_data = (struct cam_top_tpg_cfg *)tpg_hw->tpg_res.res_priv; + tpg_data->vc_num = reserv->in_port[0]->vc; + tpg_data->phy_sel = reserv->in_port[0]->lane_type; + tpg_data->num_active_lanes = reserv->in_port[0]->lane_num; + tpg_data->h_blank_count = reserv->in_port[0]->sensor_hbi; + tpg_data->v_blank_count = reserv->in_port[0]->sensor_vbi; + tpg_data->pix_pattern = reserv->in_port[0]->pix_pattern; + tpg_data->dt_cfg[0].data_type = reserv->in_port[0]->dt; + tpg_data->dt_cfg[0].frame_height = reserv->in_port[0]->height; + if (reserv->in_port[0]->usage_type) + tpg_data->dt_cfg[0].frame_width = + ((reserv->in_port[0]->right_end - + reserv->in_port[0]->left_start) + 1); + else + tpg_data->dt_cfg[0].frame_width = + reserv->in_port[0]->left_width; + tpg_data->dt_cfg[0].encode_format = encode_format; + tpg_data->num_active_dts = 1; + + CAM_DBG(CAM_ISP, + "TPG:%u vc_num:%d dt:%d phy:%d lines:%d pattern:%d format:%d", + tpg_hw->hw_intf->hw_idx, + tpg_data->vc_num, tpg_data->dt_cfg[0].data_type, + tpg_data->phy_sel, tpg_data->num_active_lanes, + tpg_data->pix_pattern, + tpg_data->dt_cfg[0].encode_format); + + CAM_DBG(CAM_ISP, "TPG:%u height:%d width:%d h blank:%d v blank:%d", + tpg_hw->hw_intf->hw_idx, + tpg_data->dt_cfg[0].frame_height, + tpg_data->dt_cfg[0].frame_width, + tpg_data->h_blank_count, + tpg_data->v_blank_count); + + if (reserv->num_inport == 1) + goto end; + + for (i = 1; i < reserv->num_inport; i++) { + if ((tpg_data->vc_num != reserv->in_port[i]->vc) || + (tpg_data->phy_sel != reserv->in_port[i]->lane_type) || + (tpg_data->num_active_lanes != + reserv->in_port[i]->lane_num) || + (tpg_data->pix_pattern != + reserv->in_port[i]->pix_pattern)) { + CAM_ERR_RATE_LIMIT(CAM_ISP, + "TPG: %u invalid DT config for tpg", + tpg_hw->hw_intf->hw_idx); + rc = -EINVAL; + goto error; + } + rc = cam_top_tpg_ver1_get_format(reserv->in_port[0]->format, + &encode_format); + if (rc) + return rc; + + tpg_data->dt_cfg[i].data_type = reserv->in_port[i]->dt; + tpg_data->dt_cfg[i].frame_height = + reserv->in_port[i]->height; + tpg_data->dt_cfg[i].frame_width = + reserv->in_port[i]->left_width; + tpg_data->dt_cfg[i].encode_format = encode_format; + tpg_data->num_active_dts++; + + CAM_DBG(CAM_ISP, "TPG:%u height:%d width:%d dt:%d format:%d", + tpg_hw->hw_intf->hw_idx, + tpg_data->dt_cfg[i].frame_height, + tpg_data->dt_cfg[i].frame_width, + tpg_data->dt_cfg[i].data_type, + tpg_data->dt_cfg[i].encode_format); + + } +end: + reserv->node_res = &tpg_hw->tpg_res; + tpg_hw->tpg_res.res_state = CAM_ISP_RESOURCE_STATE_RESERVED; +error: + mutex_unlock(&tpg_hw->hw_info->hw_mutex); + CAM_DBG(CAM_ISP, "exit rc %u", rc); + + return rc; +} + +static int cam_top_tpg_ver1_start( + void *hw_priv, + void *start_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw *tpg_hw; + struct cam_hw_info *tpg_hw_info; + struct cam_hw_soc_info *soc_info; + struct cam_isp_resource_node *tpg_res; + struct cam_top_tpg_ver1_reg_offset *tpg_reg; + struct cam_top_tpg_cfg *tpg_data; + uint32_t i, val; + + if (!hw_priv || !start_args || + (arg_size != sizeof(struct cam_isp_resource_node))) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + tpg_reg = tpg_hw->tpg_info->tpg_reg; + tpg_res = (struct cam_isp_resource_node *)start_args; + tpg_data = (struct cam_top_tpg_cfg *)tpg_res->res_priv; + soc_info = &tpg_hw->hw_info->soc_info; + + if ((tpg_res->res_type != CAM_ISP_RESOURCE_TPG) || + (tpg_res->res_state != CAM_ISP_RESOURCE_STATE_RESERVED)) { + CAM_ERR(CAM_ISP, "TPG:%d Invalid Res type:%d res_state:%d", + tpg_hw->hw_intf->hw_idx, + tpg_res->res_type, tpg_res->res_state); + rc = -EINVAL; + goto end; + } + cam_io_w_mb(0x12345678, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_lfsr_seed); + + for (i = 0; i < tpg_data->num_active_dts; i++) { + val = (((tpg_data->dt_cfg[i].frame_width & 0xFFFF) << 16) | + (tpg_data->dt_cfg[i].frame_height & 0x3FFF)); + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_dt_0_cfg_0 + 0x10 * i); + cam_io_w_mb(tpg_data->dt_cfg[i].data_type, + soc_info->reg_map[0].mem_base + + tpg_reg->tpg_dt_0_cfg_1 + 0x10 * i); + val = ((tpg_data->dt_cfg[i].encode_format & 0xF) << + tpg_reg->tpg_dt_encode_format_shift) | + tpg_reg->tpg_payload_mode_color; + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_dt_0_cfg_2 + 0x10 * i); + } + + val = (tpg_num_dt_map[tpg_data->num_active_dts-1] << + tpg_reg->tpg_num_dts_shift_val) | tpg_data->vc_num; + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_vc_cfg0); + + /* + * if hblank is notset configureHBlank count 500 and + * V blank count is 600 + */ + + if (tpg_data->h_blank_count) + cam_io_w_mb(tpg_data->h_blank_count, + soc_info->reg_map[0].mem_base + tpg_reg->tpg_vc_cfg1); + else + cam_io_w_mb(0x2581F4, + soc_info->reg_map[0].mem_base + tpg_reg->tpg_vc_cfg1); + + val = (1 << tpg_reg->tpg_split_en_shift); + cam_io_w_mb(tpg_data->pix_pattern, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_common_gen_cfg); + + /* if VBI is notset configureVBI to 0xAFF */ + if (tpg_data->v_blank_count) + cam_io_w_mb(tpg_data->v_blank_count, + soc_info->reg_map[0].mem_base + tpg_reg->tpg_vbi_cfg); + else + cam_io_w_mb(0xAFFF, + soc_info->reg_map[0].mem_base + tpg_reg->tpg_vbi_cfg); + + /* Set the TOP tpg mux sel*/ + cam_io_w_mb((1 << tpg_hw->hw_intf->hw_idx), + soc_info->reg_map[1].mem_base + tpg_reg->top_mux_reg_offset); + + val = ((tpg_data->num_active_lanes - 1) << + tpg_reg->tpg_num_active_lines_shift) | + (1 << tpg_reg->tpg_fe_pkt_en_shift) | + (1 << tpg_reg->tpg_fs_pkt_en_shift) | + (tpg_data->phy_sel << tpg_reg->tpg_phy_sel_shift_val) | + (1 << tpg_reg->tpg_en_shift_val); + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_ctrl); + + tpg_res->res_state = CAM_ISP_RESOURCE_STATE_STREAMING; + + val = cam_io_r_mb(soc_info->reg_map[0].mem_base + + tpg_reg->tpg_hw_version); + CAM_DBG(CAM_ISP, "TPG:%d TPG HW version: 0x%x started", + tpg_hw->hw_intf->hw_idx, val); + +end: + return rc; +} + +static int cam_top_tpg_ver1_stop( + void *hw_priv, + void *stop_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw *tpg_hw; + struct cam_hw_info *tpg_hw_info; + struct cam_hw_soc_info *soc_info; + struct cam_isp_resource_node *tpg_res; + const struct cam_top_tpg_ver1_reg_offset *tpg_reg; + struct cam_top_tpg_cfg *tpg_data; + + if (!hw_priv || !stop_args || + (arg_size != sizeof(struct cam_isp_resource_node))) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + tpg_reg = tpg_hw->tpg_info->tpg_reg; + tpg_res = (struct cam_isp_resource_node *) stop_args; + tpg_data = (struct cam_top_tpg_cfg *)tpg_res->res_state; + soc_info = &tpg_hw->hw_info->soc_info; + + if ((tpg_res->res_type != CAM_ISP_RESOURCE_TPG) || + (tpg_res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING)) { + CAM_DBG(CAM_ISP, "TPG:%d Invalid Res type:%d res_state:%d", + tpg_hw->hw_intf->hw_idx, + tpg_res->res_type, tpg_res->res_state); + rc = -EINVAL; + goto end; + } + + cam_io_w_mb(0, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_ctrl); + + tpg_res->res_state = CAM_ISP_RESOURCE_STATE_RESERVED; + + CAM_DBG(CAM_ISP, "TPG:%d stopped", tpg_hw->hw_intf->hw_idx); +end: + return rc; +} + +int cam_top_tpg_ver1_init( + struct cam_top_tpg_hw *tpg_hw) +{ + tpg_hw->hw_intf->hw_ops.get_hw_caps = cam_top_tpg_ver1_get_hw_caps; + tpg_hw->hw_intf->hw_ops.reserve = cam_top_tpg_ver1_reserve; + tpg_hw->hw_intf->hw_ops.start = cam_top_tpg_ver1_start; + tpg_hw->hw_intf->hw_ops.stop = cam_top_tpg_ver1_stop; + + return 0; +} diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.h new file mode 100644 index 0000000000..b0c5d68f04 --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver1.h @@ -0,0 +1,55 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +/* + * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. + */ + +#ifndef _CAM_TOP_TPG_VER1_H_ +#define _CAM_TOP_TPG_VER1_H_ + +#include "cam_top_tpg_core.h" + +struct cam_top_tpg_ver1_reg_offset { + uint32_t tpg_hw_version; + uint32_t tpg_hw_status; + uint32_t tpg_ctrl; + uint32_t tpg_vc_cfg0; + uint32_t tpg_vc_cfg1; + uint32_t tpg_lfsr_seed; + uint32_t tpg_dt_0_cfg_0; + uint32_t tpg_dt_1_cfg_0; + uint32_t tpg_dt_2_cfg_0; + uint32_t tpg_dt_3_cfg_0; + uint32_t tpg_dt_0_cfg_1; + uint32_t tpg_dt_1_cfg_1; + uint32_t tpg_dt_2_cfg_1; + uint32_t tpg_dt_3_cfg_1; + uint32_t tpg_dt_0_cfg_2; + uint32_t tpg_dt_1_cfg_2; + uint32_t tpg_dt_2_cfg_2; + uint32_t tpg_dt_3_cfg_2; + uint32_t tpg_color_bar_cfg; + uint32_t tpg_common_gen_cfg; + uint32_t tpg_vbi_cfg; + uint32_t tpg_test_bus_crtl; + uint32_t tpg_spare; + /* configurations */ + uint32_t major_version; + uint32_t minor_version; + uint32_t version_incr; + uint32_t tpg_en_shift_val; + uint32_t tpg_phy_sel_shift_val; + uint32_t tpg_num_active_lines_shift; + uint32_t tpg_fe_pkt_en_shift; + uint32_t tpg_fs_pkt_en_shift; + uint32_t tpg_line_interleaving_mode_shift; + uint32_t tpg_num_dts_shift_val; + uint32_t tpg_v_blank_cnt_shift; + uint32_t tpg_dt_encode_format_shift; + uint32_t tpg_payload_mode_color; + uint32_t tpg_split_en_shift; + uint32_t top_mux_reg_offset; +}; + +int cam_top_tpg_ver1_init(struct cam_top_tpg_hw *tpg_hw); + +#endif /* _CAM_TOP_TPG_VER1_H_ */ diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.c b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.c new file mode 100644 index 0000000000..555cebf79f --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.c @@ -0,0 +1,242 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (c) 2020, The Linux Foundation. All rights reserved. + */ + +#include +#include +#include + +#include "cam_top_tpg_core.h" +#include "cam_soc_util.h" +#include "cam_io_util.h" +#include "cam_debug_util.h" +#include "cam_top_tpg_ver2.h" + +#define CAM_TOP_TPG_VER2_MAX_SUPPORTED_DT 1 + +static int cam_top_tpg_ver2_get_hw_caps( + void *hw_priv, + void *get_hw_cap_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw_caps *hw_caps; + struct cam_top_tpg_hw *tpg_hw; + const struct cam_top_tpg_ver2_reg_offset *tpg_reg; + struct cam_hw_info *tpg_hw_info; + + if (!hw_priv || !get_hw_cap_args) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + hw_caps = (struct cam_top_tpg_hw_caps *) get_hw_cap_args; + tpg_reg = tpg_hw->tpg_info->tpg_reg; + + hw_caps->major_version = tpg_reg->major_version; + hw_caps->minor_version = tpg_reg->minor_version; + hw_caps->version_incr = tpg_reg->version_incr; + + CAM_DBG(CAM_ISP, + "TPG:%d major:%d minor:%d ver :%d", + tpg_hw->hw_intf->hw_idx, hw_caps->major_version, + hw_caps->minor_version, hw_caps->version_incr); + + return rc; +} + +static int cam_top_tpg_ver2_reserve( + void *hw_priv, + void *reserve_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw *tpg_hw; + struct cam_hw_info *tpg_hw_info; + struct cam_top_tpg_ver2_reserve_args *reserv; + struct cam_top_tpg_cfg *tpg_data; + + if (!hw_priv || !reserve_args || (arg_size != + sizeof(struct cam_top_tpg_ver2_reserve_args))) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + reserv = (struct cam_top_tpg_ver2_reserve_args *)reserve_args; + + if (reserv->num_inport <= 0 || + reserv->num_inport > CAM_TOP_TPG_VER2_MAX_SUPPORTED_DT) { + CAM_ERR_RATE_LIMIT(CAM_ISP, "TPG: %u invalid input num port:%d", + tpg_hw->hw_intf->hw_idx, reserv->num_inport); + return -EINVAL; + } + + mutex_lock(&tpg_hw->hw_info->hw_mutex); + if (tpg_hw->tpg_res.res_state != CAM_ISP_RESOURCE_STATE_AVAILABLE) { + CAM_ERR(CAM_ISP, "TPG:%d resource not available state:%d", + tpg_hw->hw_intf->hw_idx, tpg_hw->tpg_res.res_state); + mutex_unlock(&tpg_hw->hw_info->hw_mutex); + return -EINVAL; + } + + tpg_data = (struct cam_top_tpg_cfg *)tpg_hw->tpg_res.res_priv; + tpg_data->h_blank_count = reserv->in_port->hbi_cnt; + tpg_data->v_blank_count = 600; + tpg_data->dt_cfg[0].data_type = reserv->in_port->dt[0]; + tpg_data->dt_cfg[0].frame_height = reserv->in_port->height; + if (reserv->in_port->usage_type) + tpg_data->dt_cfg[0].frame_width = + ((reserv->in_port->right_stop - + reserv->in_port->left_start) + 1); + else + tpg_data->dt_cfg[0].frame_width = + reserv->in_port->left_width; + tpg_data->num_active_dts = 1; + + CAM_DBG(CAM_ISP, "TPG:%u dt:0x%x h:%d w:%d hbi:%d vbi:%d reserved", + tpg_hw->hw_intf->hw_idx, + tpg_data->dt_cfg[0].data_type, + tpg_data->dt_cfg[0].frame_height, + tpg_data->dt_cfg[0].frame_width, + tpg_data->h_blank_count, + tpg_data->v_blank_count); + + reserv->node_res = &tpg_hw->tpg_res; + tpg_hw->tpg_res.res_state = CAM_ISP_RESOURCE_STATE_RESERVED; + + mutex_unlock(&tpg_hw->hw_info->hw_mutex); + + return rc; +} + +static int cam_top_tpg_ver2_start( + void *hw_priv, + void *start_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw *tpg_hw; + struct cam_hw_info *tpg_hw_info; + struct cam_hw_soc_info *soc_info; + struct cam_isp_resource_node *tpg_res; + struct cam_top_tpg_ver2_reg_offset *tpg_reg; + struct cam_top_tpg_cfg *tpg_data; + uint32_t val; + uint32_t mux_sel_shift = 0; + + if (!hw_priv || !start_args || + (arg_size != sizeof(struct cam_isp_resource_node))) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + tpg_reg = tpg_hw->tpg_info->tpg_reg; + tpg_res = (struct cam_isp_resource_node *)start_args; + tpg_data = (struct cam_top_tpg_cfg *)tpg_res->res_priv; + soc_info = &tpg_hw->hw_info->soc_info; + + if ((tpg_res->res_type != CAM_ISP_RESOURCE_TPG) || + (tpg_res->res_state != CAM_ISP_RESOURCE_STATE_RESERVED)) { + CAM_ERR(CAM_ISP, "TPG:%d Invalid Res type:%d res_state:%d", + tpg_hw->hw_intf->hw_idx, + tpg_res->res_type, tpg_res->res_state); + rc = -EINVAL; + goto end; + } + + if (tpg_hw->hw_intf->hw_idx == CAM_TOP_TPG_ID_0) + mux_sel_shift = tpg_reg->tpg_mux_sel_tpg_0_shift; + else if (tpg_hw->hw_intf->hw_idx == CAM_TOP_TPG_ID_1) + mux_sel_shift = tpg_reg->tpg_mux_sel_tpg_1_shift; + + cam_io_w_mb((tpg_reg->tpg_mux_sel_en << mux_sel_shift), + soc_info->reg_map[1].mem_base + tpg_reg->top_mux_sel); + + val = (((tpg_data->dt_cfg[0].frame_width & 0x3FFF) << 16) | + (tpg_data->dt_cfg[0].frame_height & 0x3FFF)); + + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_cfg_0); + + val = (tpg_data->h_blank_count & 0x7FF) << 20; + val |= (tpg_data->v_blank_count & 0x3FFFF); + + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_cfg_1); + + val = tpg_data->dt_cfg[0].data_type << 11; + cam_io_w_mb(val, soc_info->reg_map[0].mem_base + tpg_reg->tpg_cfg_2); + + /* program number of frames */ + cam_io_w_mb(1, soc_info->reg_map[0].mem_base + tpg_reg->tpg_cfg_3); + + cam_io_w_mb(tpg_reg->tpg_module_en, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_module_cfg); + + tpg_res->res_state = CAM_ISP_RESOURCE_STATE_STREAMING; + CAM_DBG(CAM_ISP, "TPG:%d started", tpg_hw->hw_intf->hw_idx); + +end: + return rc; +} + +static int cam_top_tpg_ver2_stop( + void *hw_priv, + void *stop_args, + uint32_t arg_size) +{ + int rc = 0; + struct cam_top_tpg_hw *tpg_hw; + struct cam_hw_info *tpg_hw_info; + struct cam_hw_soc_info *soc_info; + struct cam_isp_resource_node *tpg_res; + const struct cam_top_tpg_ver2_reg_offset *tpg_reg; + struct cam_top_tpg_cfg *tpg_data; + + if (!hw_priv || !stop_args || + (arg_size != sizeof(struct cam_isp_resource_node))) { + CAM_ERR(CAM_ISP, "TPG: Invalid args"); + return -EINVAL; + } + + tpg_hw_info = (struct cam_hw_info *)hw_priv; + tpg_hw = (struct cam_top_tpg_hw *)tpg_hw_info->core_info; + tpg_reg = tpg_hw->tpg_info->tpg_reg; + tpg_res = (struct cam_isp_resource_node *) stop_args; + tpg_data = (struct cam_top_tpg_cfg *)tpg_res->res_state; + soc_info = &tpg_hw->hw_info->soc_info; + + if ((tpg_res->res_type != CAM_ISP_RESOURCE_TPG) || + (tpg_res->res_state != CAM_ISP_RESOURCE_STATE_STREAMING)) { + CAM_DBG(CAM_ISP, "TPG:%d Invalid Res type:%d res_state:%d", + tpg_hw->hw_intf->hw_idx, + tpg_res->res_type, tpg_res->res_state); + rc = -EINVAL; + goto end; + } + + cam_io_w_mb(0, soc_info->reg_map[0].mem_base + + tpg_reg->tpg_module_cfg); + + tpg_res->res_state = CAM_ISP_RESOURCE_STATE_RESERVED; + + CAM_DBG(CAM_ISP, "TPG:%d stopped", tpg_hw->hw_intf->hw_idx); +end: + return rc; +} + +int cam_top_tpg_ver2_init( + struct cam_top_tpg_hw *tpg_hw) +{ + tpg_hw->hw_intf->hw_ops.get_hw_caps = cam_top_tpg_ver2_get_hw_caps; + tpg_hw->hw_intf->hw_ops.reserve = cam_top_tpg_ver2_reserve; + tpg_hw->hw_intf->hw_ops.start = cam_top_tpg_ver2_start; + tpg_hw->hw_intf->hw_ops.stop = cam_top_tpg_ver2_stop; + + return 0; +} diff --git a/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.h b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.h new file mode 100644 index 0000000000..698ebf9e3f --- /dev/null +++ b/drivers/cam_isp/isp_hw_mgr/isp_hw/top_tpg/cam_top_tpg_ver2.h @@ -0,0 +1,44 @@ +/* SPDX-License-Identifier: GPL-2.0-only */ +/* + * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. + */ + +#ifndef _CAM_TOP_TPG_VER2_H_ +#define _CAM_TOP_TPG_VER2_H_ + +#include "cam_top_tpg_core.h" + +struct cam_top_tpg_ver2_reg_offset { + uint32_t tpg_hw_version; + uint32_t tpg_hw_status; + uint32_t tpg_module_cfg; + uint32_t tpg_cfg_0; + uint32_t tpg_cfg_1; + uint32_t tpg_cfg_2; + uint32_t tpg_cfg_3; + uint32_t tpg_spare; + uint32_t top_mux_sel; + /* configurations */ + uint32_t major_version; + uint32_t minor_version; + uint32_t version_incr; + uint32_t tpg_module_en; + uint32_t tpg_mux_sel_en; + uint32_t tpg_mux_sel_tpg_0_shift; + uint32_t tpg_mux_sel_tpg_1_shift; + uint32_t tpg_en_shift_val; + uint32_t tpg_phy_sel_shift_val; + uint32_t tpg_num_active_lines_shift; + uint32_t tpg_fe_pkt_en_shift; + uint32_t tpg_fs_pkt_en_shift; + uint32_t tpg_line_interleaving_mode_shift; + uint32_t tpg_num_dts_shift_val; + uint32_t tpg_v_blank_cnt_shift; + uint32_t tpg_dt_encode_format_shift; + uint32_t tpg_payload_mode_color; + uint32_t tpg_split_en_shift; +}; + +int cam_top_tpg_ver2_init(struct cam_top_tpg_hw *tpg_hw); + +#endif /* _CAM_TOP_TPG_VER2_H_ */ diff --git a/drivers/camera_main.c b/drivers/camera_main.c index 1dfe51a7ad..35bd853f44 100644 --- a/drivers/camera_main.c +++ b/drivers/camera_main.c @@ -50,7 +50,7 @@ #include "ope_dev_intf.h" -#include "cam_top_tpg_v1.h" +#include "cam_top_tpg.h" #include "cam_tfe_dev.h" #include "cam_tfe_csid530.h" #include "camera_main.h" @@ -77,6 +77,7 @@ static const struct camera_submodule_component camera_base[] = { static const struct camera_submodule_component camera_isp[] = { #ifdef CONFIG_SPECTRA_ISP + {&cam_top_tpg_init_module, &cam_top_tpg_exit_module}, {&cam_ife_csid17x_init_module, &cam_ife_csid17x_exit_module}, {&cam_ife_csid_lite_init_module, &cam_ife_csid_lite_exit_module}, {&cam_vfe_init_module, &cam_vfe_exit_module}, @@ -86,7 +87,7 @@ static const struct camera_submodule_component camera_isp[] = { static const struct camera_submodule_component camera_tfe[] = { #if IS_ENABLED(CONFIG_SPECTRA_TFE) - {&cam_top_tpg_v1_init_module, &cam_top_tpg_v1_exit_module}, + {&cam_top_tpg_init_module, &cam_top_tpg_exit_module}, {&cam_tfe_init_module, &cam_tfe_exit_module}, {&cam_tfe_csid530_init_module, &cam_tfe_csid530_exit_module}, #endif @@ -218,13 +219,14 @@ static struct platform_driver *const cam_component_drivers[] = { &cam_cdm_intf_driver, &cam_hw_cdm_driver, #ifdef CONFIG_SPECTRA_ISP + &cam_top_tpg_driver, &cam_ife_csid17x_driver, &cam_ife_csid_lite_driver, &cam_vfe_driver, &isp_driver, #endif #ifdef CONFIG_SPECTRA_TFE - &cam_top_tpg_v1_driver, + &cam_top_tpg_driver, &cam_tfe_driver, &cam_tfe_csid530_driver, #endif diff --git a/drivers/camera_main.h b/drivers/camera_main.h index 8787c8786c..3de446d08b 100644 --- a/drivers/camera_main.h +++ b/drivers/camera_main.h @@ -15,13 +15,14 @@ extern struct platform_driver cam_cpas_driver; extern struct platform_driver cam_cdm_intf_driver; extern struct platform_driver cam_hw_cdm_driver; #ifdef CONFIG_SPECTRA_ISP +extern struct platform_driver cam_top_tpg_driver; extern struct platform_driver cam_ife_csid17x_driver; extern struct platform_driver cam_ife_csid_lite_driver; extern struct platform_driver cam_vfe_driver; extern struct platform_driver isp_driver; #endif #ifdef CONFIG_SPECTRA_TFE -extern struct platform_driver cam_top_tpg_v1_driver; +extern struct platform_driver cam_top_tpg_driver; extern struct platform_driver cam_tfe_driver; extern struct platform_driver cam_tfe_csid530_driver; #endif diff --git a/include/uapi/camera/media/cam_isp_ife.h b/include/uapi/camera/media/cam_isp_ife.h index 34c1b3bd2b..f18a474bc7 100644 --- a/include/uapi/camera/media/cam_isp_ife.h +++ b/include/uapi/camera/media/cam_isp_ife.h @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0-only WITH Linux-syscall-note */ /* - * Copyright (c) 2016-2019, The Linux Foundation. All rights reserved. + * Copyright (c) 2016-2020, The Linux Foundation. All rights reserved. */ #ifndef __UAPI_CAM_ISP_IFE_H__ @@ -49,6 +49,8 @@ #define CAM_ISP_IFE_IN_RES_PHY_4 (CAM_ISP_IFE_IN_RES_BASE + 5) #define CAM_ISP_IFE_IN_RES_PHY_5 (CAM_ISP_IFE_IN_RES_BASE + 6) #define CAM_ISP_IFE_IN_RES_RD (CAM_ISP_IFE_IN_RES_BASE + 7) -#define CAM_ISP_IFE_IN_RES_MAX (CAM_ISP_IFE_IN_RES_BASE + 8) +#define CAM_ISP_IFE_IN_RES_CPHY_TPG_0 (CAM_ISP_IFE_IN_RES_BASE + 8) +#define CAM_ISP_IFE_IN_RES_CPHY_TPG_1 (CAM_ISP_IFE_IN_RES_BASE + 9) +#define CAM_ISP_IFE_IN_RES_MAX (CAM_ISP_IFE_IN_RES_BASE + 10) #endif /* __UAPI_CAM_ISP_IFE_H__ */