All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 00/55] media: rkisp1: Cleanups and add support for i.MX8MP
@ 2022-06-14 19:10 ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello,

This series depends on v4 of "media: rkisp1: Misc bug fixes and cleanups" [1].

The ISP integrated in the i.MX8MP is nearly the same as the rkisp1, and
so we can reuse the rkisp1 driver for it.

This series does some cleanup and refactoring of the rkisp1 driver,
(patches 1/55 to 46/55), and then adds support for the i.MX8MP (patches
47/55 to 55/55).


Paul

[1] https://lore.kernel.org/linux-media/Ymbxs2p9Tuf331qM@pendragon.ideasonboard.com/T/

Laurent Pinchart (38):
  media: rkisp1: Enable compilation on ARCH_MXC
  media: rkisp1: Disable runtime PM in probe error path
  media: rkisp1: Read the ID register at probe time instead of streamon
  media: rkisp1: Rename rkisp1_match_data to rkisp1_info
  media: rkisp1: Access ISP version from info pointer
  media: rkisp1: cap: Print debug message on failed link validation
  media: rkisp1: Move sensor .s_stream() call to ISP
  media: rkisp1: Reject sensors without pixel rate control at bound time
  media: rkisp1: Create link from sensor to ISP at notifier bound time
  media: rkisp1: Create internal links at probe time
  media: rkisp1: Rename rkisp1_subdev_notifier() to
    rkisp1_subdev_notifier_register()
  media: v4l2-async: Add notifier operation to destroy asd instances
  media: rkisp1: Fix sensor source pad retrieval at bound time
  media: rkisp1: isp: Start CSI-2 receiver before ISP
  media: rkisp1: csi: Handle CSI-2 RX configuration fully in
    rkisp1-csi.c
  media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi
    prefix
  media: rkisp1: csi: Move start delay to rkisp1_csi_start()
  media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
  media: rkisp1: csi: Constify argument to rkisp1_csi_start()
  media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
  media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
  media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
  media: rkisp1: isp: Add container_of wrapper to cast subdev to
    rkisp1_isp
  media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
  media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
  media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
  media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single
    variable
  media: rkisp1: isp: Initialize some variables at declaration time
  media: rkisp1: isp: Fix whitespace issues
  media: rkisp1: isp: Constify various local variables
  media: rkisp1: isp: Rename rkisp1_get_remote_source()
  media: mc-entity: Add a new helper function to get a remote pad
  media: mc-entity: Add a new helper function to get a remote pad for a
    pad
  media: rkisp1: isp: Disallow multiple active sources
  media: rkisp1: csi: Plumb the CSI RX subdev
  media: rkisp1: Add infrastructure to support ISP features
  media: rkisp1: Make the internal CSI-2 receiver optional
  media: rkisp1: Configure gasket on i.MX8MP

Paul Elder (17):
  media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
  media: rkisp1: debug: Add debugfs files to monitor MI and ISP
    interrupts
  media: rkisp1: Save info pointer in rkisp1_device
  media: rkisp1: Make rkisp1_isp_mbus_info common
  media: rkisp1: Split CSI handling to separate file
  media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
  media: rkisp1: Use fwnode_graph_for_each_endpoint
  dt-bindings: media: rkisp1: Add port for parallel interface
  media: rkisp1: Support the ISP parallel input
  dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
  media: rkisp1: Add match data for i.MX8MP ISP
  media: rkisp1: Add and set registers for crop for i.MX8MP
  media: rkisp1: Add and set registers for output size config on i.MX8MP
  media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
  media: rkisp1: Shift DMA buffer addresses on i.MX8MP
  media: rkisp1: Add register definitions for the test pattern generator
  media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP

 .../bindings/media/rockchip-isp1.yaml         |  30 +-
 Documentation/driver-api/media/mc-core.rst    |   4 +-
 .../driver-api/media/v4l2-subdev.rst          |   6 +
 drivers/media/mc/mc-entity.c                  |  69 ++
 .../media/platform/rockchip/rkisp1/Kconfig    |   2 +-
 .../media/platform/rockchip/rkisp1/Makefile   |   1 +
 .../platform/rockchip/rkisp1/rkisp1-capture.c |  49 +-
 .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 ++++
 .../platform/rockchip/rkisp1/rkisp1-common.h  | 130 +++-
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 525 ++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +
 .../platform/rockchip/rkisp1/rkisp1-debug.c   |  55 +-
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 440 +++++++-----
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 679 +++++++-----------
 .../platform/rockchip/rkisp1/rkisp1-params.c  |   2 +-
 .../platform/rockchip/rkisp1/rkisp1-regs.h    |  87 +++
 .../platform/rockchip/rkisp1/rkisp1-resizer.c |  43 +-
 .../platform/rockchip/rkisp1/rkisp1-stats.c   |   4 +-
 drivers/media/v4l2-core/v4l2-async.c          |  10 +
 include/media/media-entity.h                  |  63 ++
 include/media/v4l2-async.h                    |   2 +
 include/uapi/linux/rkisp1-config.h            |   3 +
 22 files changed, 1735 insertions(+), 645 deletions(-)
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h

-- 
2.30.2


^ permalink raw reply	[flat|nested] 298+ messages in thread

* [PATCH 00/55] media: rkisp1: Cleanups and add support for i.MX8MP
@ 2022-06-14 19:10 ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello,

This series depends on v4 of "media: rkisp1: Misc bug fixes and cleanups" [1].

The ISP integrated in the i.MX8MP is nearly the same as the rkisp1, and
so we can reuse the rkisp1 driver for it.

This series does some cleanup and refactoring of the rkisp1 driver,
(patches 1/55 to 46/55), and then adds support for the i.MX8MP (patches
47/55 to 55/55).


Paul

[1] https://lore.kernel.org/linux-media/Ymbxs2p9Tuf331qM@pendragon.ideasonboard.com/T/

Laurent Pinchart (38):
  media: rkisp1: Enable compilation on ARCH_MXC
  media: rkisp1: Disable runtime PM in probe error path
  media: rkisp1: Read the ID register at probe time instead of streamon
  media: rkisp1: Rename rkisp1_match_data to rkisp1_info
  media: rkisp1: Access ISP version from info pointer
  media: rkisp1: cap: Print debug message on failed link validation
  media: rkisp1: Move sensor .s_stream() call to ISP
  media: rkisp1: Reject sensors without pixel rate control at bound time
  media: rkisp1: Create link from sensor to ISP at notifier bound time
  media: rkisp1: Create internal links at probe time
  media: rkisp1: Rename rkisp1_subdev_notifier() to
    rkisp1_subdev_notifier_register()
  media: v4l2-async: Add notifier operation to destroy asd instances
  media: rkisp1: Fix sensor source pad retrieval at bound time
  media: rkisp1: isp: Start CSI-2 receiver before ISP
  media: rkisp1: csi: Handle CSI-2 RX configuration fully in
    rkisp1-csi.c
  media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi
    prefix
  media: rkisp1: csi: Move start delay to rkisp1_csi_start()
  media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
  media: rkisp1: csi: Constify argument to rkisp1_csi_start()
  media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
  media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
  media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
  media: rkisp1: isp: Add container_of wrapper to cast subdev to
    rkisp1_isp
  media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
  media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
  media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
  media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single
    variable
  media: rkisp1: isp: Initialize some variables at declaration time
  media: rkisp1: isp: Fix whitespace issues
  media: rkisp1: isp: Constify various local variables
  media: rkisp1: isp: Rename rkisp1_get_remote_source()
  media: mc-entity: Add a new helper function to get a remote pad
  media: mc-entity: Add a new helper function to get a remote pad for a
    pad
  media: rkisp1: isp: Disallow multiple active sources
  media: rkisp1: csi: Plumb the CSI RX subdev
  media: rkisp1: Add infrastructure to support ISP features
  media: rkisp1: Make the internal CSI-2 receiver optional
  media: rkisp1: Configure gasket on i.MX8MP

Paul Elder (17):
  media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
  media: rkisp1: debug: Add debugfs files to monitor MI and ISP
    interrupts
  media: rkisp1: Save info pointer in rkisp1_device
  media: rkisp1: Make rkisp1_isp_mbus_info common
  media: rkisp1: Split CSI handling to separate file
  media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
  media: rkisp1: Use fwnode_graph_for_each_endpoint
  dt-bindings: media: rkisp1: Add port for parallel interface
  media: rkisp1: Support the ISP parallel input
  dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
  media: rkisp1: Add match data for i.MX8MP ISP
  media: rkisp1: Add and set registers for crop for i.MX8MP
  media: rkisp1: Add and set registers for output size config on i.MX8MP
  media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
  media: rkisp1: Shift DMA buffer addresses on i.MX8MP
  media: rkisp1: Add register definitions for the test pattern generator
  media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP

 .../bindings/media/rockchip-isp1.yaml         |  30 +-
 Documentation/driver-api/media/mc-core.rst    |   4 +-
 .../driver-api/media/v4l2-subdev.rst          |   6 +
 drivers/media/mc/mc-entity.c                  |  69 ++
 .../media/platform/rockchip/rkisp1/Kconfig    |   2 +-
 .../media/platform/rockchip/rkisp1/Makefile   |   1 +
 .../platform/rockchip/rkisp1/rkisp1-capture.c |  49 +-
 .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 ++++
 .../platform/rockchip/rkisp1/rkisp1-common.h  | 130 +++-
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 525 ++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +
 .../platform/rockchip/rkisp1/rkisp1-debug.c   |  55 +-
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 440 +++++++-----
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 679 +++++++-----------
 .../platform/rockchip/rkisp1/rkisp1-params.c  |   2 +-
 .../platform/rockchip/rkisp1/rkisp1-regs.h    |  87 +++
 .../platform/rockchip/rkisp1/rkisp1-resizer.c |  43 +-
 .../platform/rockchip/rkisp1/rkisp1-stats.c   |   4 +-
 drivers/media/v4l2-core/v4l2-async.c          |  10 +
 include/media/media-entity.h                  |  63 ++
 include/media/v4l2-async.h                    |   2 +
 include/uapi/linux/rkisp1-config.h            |   3 +
 22 files changed, 1735 insertions(+), 645 deletions(-)
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h

-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add a register dump file in debugfs for some of the buffer-related
registers in MI, for the base address, the size, and the offset. Also
dump the appropriate shadow registers.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
index e76dc2b164b6..1a59c00fabdd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
@@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
 }
 DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
 
+static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
+{
+	static const struct rkisp1_debug_register registers[] = {
+		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
+		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
+		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
+		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
+		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
+		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
+		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
+		{ /* Sentinel */ },
+	};
+	struct rkisp1_device *rkisp1 = m->private;
+
+	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
+}
+DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
+
 #define RKISP1_DEBUG_DATA_COUNT_BINS	32
 #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
 
@@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
 	debugfs_create_file("srsz", 0444, regs_dir,
 			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
 			    &rkisp1_debug_dump_rsz_regs_fops);
+
+	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
+			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);
 }
 
 void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add a register dump file in debugfs for some of the buffer-related
registers in MI, for the base address, the size, and the offset. Also
dump the appropriate shadow registers.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
index e76dc2b164b6..1a59c00fabdd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
@@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
 }
 DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
 
+static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
+{
+	static const struct rkisp1_debug_register registers[] = {
+		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
+		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
+		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
+		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
+		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
+		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
+		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
+		{ /* Sentinel */ },
+	};
+	struct rkisp1_device *rkisp1 = m->private;
+
+	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
+}
+DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
+
 #define RKISP1_DEBUG_DATA_COUNT_BINS	32
 #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
 
@@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
 	debugfs_create_file("srsz", 0444, regs_dir,
 			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
 			    &rkisp1_debug_dump_rsz_regs_fops);
+
+	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
+			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);
 }
 
 void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 02/55] media: rkisp1: Enable compilation on ARCH_MXC
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP used by the Rockchip RK3399 is also found in the NXP i.MX8MP.
Enable compilation of the driver for the MXC architecture in addition to
ARCH_ROCKCHIP.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/Kconfig | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/Kconfig b/drivers/media/platform/rockchip/rkisp1/Kconfig
index dabd7e42c193..731c9acbf6ef 100644
--- a/drivers/media/platform/rockchip/rkisp1/Kconfig
+++ b/drivers/media/platform/rockchip/rkisp1/Kconfig
@@ -3,7 +3,7 @@ config VIDEO_ROCKCHIP_ISP1
 	tristate "Rockchip Image Signal Processing v1 Unit driver"
 	depends on V4L_PLATFORM_DRIVERS
 	depends on VIDEO_DEV && OF
-	depends on ARCH_ROCKCHIP || COMPILE_TEST
+	depends on ARCH_ROCKCHIP || ARCH_MXC || COMPILE_TEST
 	select MEDIA_CONTROLLER
 	select VIDEO_V4L2_SUBDEV_API
 	select VIDEOBUF2_DMA_CONTIG
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 02/55] media: rkisp1: Enable compilation on ARCH_MXC
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP used by the Rockchip RK3399 is also found in the NXP i.MX8MP.
Enable compilation of the driver for the MXC architecture in addition to
ARCH_ROCKCHIP.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/Kconfig | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/Kconfig b/drivers/media/platform/rockchip/rkisp1/Kconfig
index dabd7e42c193..731c9acbf6ef 100644
--- a/drivers/media/platform/rockchip/rkisp1/Kconfig
+++ b/drivers/media/platform/rockchip/rkisp1/Kconfig
@@ -3,7 +3,7 @@ config VIDEO_ROCKCHIP_ISP1
 	tristate "Rockchip Image Signal Processing v1 Unit driver"
 	depends on V4L_PLATFORM_DRIVERS
 	depends on VIDEO_DEV && OF
-	depends on ARCH_ROCKCHIP || COMPILE_TEST
+	depends on ARCH_ROCKCHIP || ARCH_MXC || COMPILE_TEST
 	select MEDIA_CONTROLLER
 	select VIDEO_V4L2_SUBDEV_API
 	select VIDEOBUF2_DMA_CONTIG
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add files in debugfs to monitor some of the interrupts of the MI and
ISP. Add the appropriate holder variables in the rkisp1_debug struct as
well.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  9 +++++++++
 .../platform/rockchip/rkisp1/rkisp1-debug.c   | 20 +++++++++++++++++++
 2 files changed, 29 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 4243ff5e2197..a67fe7b1dfa1 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -364,6 +364,15 @@ struct rkisp1_debug {
 	unsigned long stats_error;
 	unsigned long stop_timeout[2];
 	unsigned long frame_drop[2];
+	unsigned long mi_irq_mblk_line_count;
+	unsigned long mi_irq_fill_mp_y_count;
+	unsigned long mi_irq_frame_count;
+	unsigned long mi_irq_wrap_mp_y_count;
+	unsigned long mi_irq_wrap_mp_cb_count;
+	unsigned long mi_irq_wrap_mp_cr_count;
+	unsigned long isp_irq_v_start_count;
+	unsigned long isp_irq_frame_count;
+	unsigned long isp_irq_frame_in_count;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
index 1a59c00fabdd..02854e8ea1a4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
@@ -220,6 +220,26 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
 	debugfs_create_file("input_status", 0444, debug->debugfs_dir, rkisp1,
 			    &rkisp1_debug_input_status_fops);
 
+	debugfs_create_ulong("mi_irq_mblk_line_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_mblk_line_count);
+	debugfs_create_ulong("mi_irq_fill_mp_y_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_fill_mp_y_count);
+	debugfs_create_ulong("mi_irq_frame_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_frame_count);
+	debugfs_create_ulong("mi_irq_wrap_mp_y_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_wrap_mp_y_count);
+	debugfs_create_ulong("mi_irq_wrap_mp_cb_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_wrap_mp_cb_count);
+	debugfs_create_ulong("mi_irq_wrap_mp_cr_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_wrap_mp_cr_count);
+
+	debugfs_create_ulong("isp_irq_v_start_count", 0444, debug->debugfs_dir,
+			     &debug->isp_irq_v_start_count);
+	debugfs_create_ulong("isp_irq_frame_count", 0444, debug->debugfs_dir,
+			     &debug->isp_irq_frame_count);
+	debugfs_create_ulong("isp_irq_frame_in_count", 0444, debug->debugfs_dir,
+			     &debug->isp_irq_frame_in_count);
+
 	regs_dir = debugfs_create_dir("regs", debug->debugfs_dir);
 
 	debugfs_create_file("core", 0444, regs_dir, rkisp1,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add files in debugfs to monitor some of the interrupts of the MI and
ISP. Add the appropriate holder variables in the rkisp1_debug struct as
well.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  9 +++++++++
 .../platform/rockchip/rkisp1/rkisp1-debug.c   | 20 +++++++++++++++++++
 2 files changed, 29 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 4243ff5e2197..a67fe7b1dfa1 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -364,6 +364,15 @@ struct rkisp1_debug {
 	unsigned long stats_error;
 	unsigned long stop_timeout[2];
 	unsigned long frame_drop[2];
+	unsigned long mi_irq_mblk_line_count;
+	unsigned long mi_irq_fill_mp_y_count;
+	unsigned long mi_irq_frame_count;
+	unsigned long mi_irq_wrap_mp_y_count;
+	unsigned long mi_irq_wrap_mp_cb_count;
+	unsigned long mi_irq_wrap_mp_cr_count;
+	unsigned long isp_irq_v_start_count;
+	unsigned long isp_irq_frame_count;
+	unsigned long isp_irq_frame_in_count;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
index 1a59c00fabdd..02854e8ea1a4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
@@ -220,6 +220,26 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
 	debugfs_create_file("input_status", 0444, debug->debugfs_dir, rkisp1,
 			    &rkisp1_debug_input_status_fops);
 
+	debugfs_create_ulong("mi_irq_mblk_line_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_mblk_line_count);
+	debugfs_create_ulong("mi_irq_fill_mp_y_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_fill_mp_y_count);
+	debugfs_create_ulong("mi_irq_frame_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_frame_count);
+	debugfs_create_ulong("mi_irq_wrap_mp_y_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_wrap_mp_y_count);
+	debugfs_create_ulong("mi_irq_wrap_mp_cb_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_wrap_mp_cb_count);
+	debugfs_create_ulong("mi_irq_wrap_mp_cr_count", 0444, debug->debugfs_dir,
+			     &debug->mi_irq_wrap_mp_cr_count);
+
+	debugfs_create_ulong("isp_irq_v_start_count", 0444, debug->debugfs_dir,
+			     &debug->isp_irq_v_start_count);
+	debugfs_create_ulong("isp_irq_frame_count", 0444, debug->debugfs_dir,
+			     &debug->isp_irq_frame_count);
+	debugfs_create_ulong("isp_irq_frame_in_count", 0444, debug->debugfs_dir,
+			     &debug->isp_irq_frame_in_count);
+
 	regs_dir = debugfs_create_dir("regs", debug->debugfs_dir);
 
 	debugfs_create_file("core", 0444, regs_dir, rkisp1,
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 04/55] media: rkisp1: Disable runtime PM in probe error path
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

If the v4l2_device_register() call fails, runtime PM is left enabled.
Fix it.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 97d569968285..248f0172ca62 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -523,7 +523,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 
 	ret = v4l2_device_register(rkisp1->dev, &rkisp1->v4l2_dev);
 	if (ret)
-		return ret;
+		goto err_pm_runtime_disable;
 
 	ret = media_device_register(&rkisp1->media_dev);
 	if (ret) {
@@ -543,6 +543,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 	media_device_unregister(&rkisp1->media_dev);
 err_unreg_v4l2_dev:
 	v4l2_device_unregister(&rkisp1->v4l2_dev);
+err_pm_runtime_disable:
 	pm_runtime_disable(&pdev->dev);
 	return ret;
 }
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 04/55] media: rkisp1: Disable runtime PM in probe error path
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

If the v4l2_device_register() call fails, runtime PM is left enabled.
Fix it.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 97d569968285..248f0172ca62 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -523,7 +523,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 
 	ret = v4l2_device_register(rkisp1->dev, &rkisp1->v4l2_dev);
 	if (ret)
-		return ret;
+		goto err_pm_runtime_disable;
 
 	ret = media_device_register(&rkisp1->media_dev);
 	if (ret) {
@@ -543,6 +543,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 	media_device_unregister(&rkisp1->media_dev);
 err_unreg_v4l2_dev:
 	v4l2_device_unregister(&rkisp1->v4l2_dev);
+err_pm_runtime_disable:
 	pm_runtime_disable(&pdev->dev);
 	return ret;
 }
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 05/55] media: rkisp1: Read the ID register at probe time instead of streamon
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

There's no need to read the ID register every time streaming is started.
Do it once, at probe time.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 10 ++++++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c |  4 ----
 2 files changed, 10 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 248f0172ca62..ba773c0784fb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -467,6 +467,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 	struct v4l2_device *v4l2_dev;
 	unsigned int i;
 	int ret, irq;
+	u32 cif_id;
 
 	match_data = of_device_get_match_data(&pdev->dev);
 	if (!match_data)
@@ -509,6 +510,15 @@ static int rkisp1_probe(struct platform_device *pdev)
 
 	pm_runtime_enable(&pdev->dev);
 
+	ret = pm_runtime_resume_and_get(&pdev->dev);
+	if (ret)
+		goto err_pm_runtime_disable;
+
+	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
+	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
+
+	pm_runtime_put(&pdev->dev);
+
 	rkisp1->media_dev.hw_revision = match_data->isp_ver;
 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
 		sizeof(rkisp1->media_dev.model));
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 187d78075acb..02968656f3c0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -473,12 +473,8 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 /* Hardware configure Entry */
 static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
 {
-	u32 cif_id;
 	int ret;
 
-	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
-	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
-
 	ret = rkisp1_config_isp(rkisp1);
 	if (ret)
 		return ret;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 05/55] media: rkisp1: Read the ID register at probe time instead of streamon
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

There's no need to read the ID register every time streaming is started.
Do it once, at probe time.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 10 ++++++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c |  4 ----
 2 files changed, 10 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 248f0172ca62..ba773c0784fb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -467,6 +467,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 	struct v4l2_device *v4l2_dev;
 	unsigned int i;
 	int ret, irq;
+	u32 cif_id;
 
 	match_data = of_device_get_match_data(&pdev->dev);
 	if (!match_data)
@@ -509,6 +510,15 @@ static int rkisp1_probe(struct platform_device *pdev)
 
 	pm_runtime_enable(&pdev->dev);
 
+	ret = pm_runtime_resume_and_get(&pdev->dev);
+	if (ret)
+		goto err_pm_runtime_disable;
+
+	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
+	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
+
+	pm_runtime_put(&pdev->dev);
+
 	rkisp1->media_dev.hw_revision = match_data->isp_ver;
 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
 		sizeof(rkisp1->media_dev.model));
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 187d78075acb..02968656f3c0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -473,12 +473,8 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 /* Hardware configure Entry */
 static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
 {
-	u32 cif_id;
 	int ret;
 
-	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
-	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
-
 	ret = rkisp1_config_isp(rkisp1);
 	if (ret)
 		return ret;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 06/55] media: rkisp1: Rename rkisp1_match_data to rkisp1_info
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1_match_data structure contains device model-specific
information. It it referenced from OF match data, but that's an
implementation detail. Rename it to rkisp1_info to reflect its main
purpose.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 34 +++++++++----------
 1 file changed, 17 insertions(+), 17 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index ba773c0784fb..258980ef4783 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -105,7 +105,7 @@ struct rkisp1_isr_data {
 	irqreturn_t (*isr)(int irq, void *ctx);
 };
 
-struct rkisp1_match_data {
+struct rkisp1_info {
 	const char * const *clks;
 	unsigned int clk_size;
 	const struct rkisp1_isr_data *isrs;
@@ -420,7 +420,7 @@ static const struct rkisp1_isr_data px30_isp_isrs[] = {
 	{ "mipi", rkisp1_mipi_isr },
 };
 
-static const struct rkisp1_match_data px30_isp_match_data = {
+static const struct rkisp1_info px30_isp_info = {
 	.clks = px30_isp_clks,
 	.clk_size = ARRAY_SIZE(px30_isp_clks),
 	.isrs = px30_isp_isrs,
@@ -438,7 +438,7 @@ static const struct rkisp1_isr_data rk3399_isp_isrs[] = {
 	{ NULL, rkisp1_isr },
 };
 
-static const struct rkisp1_match_data rk3399_isp_match_data = {
+static const struct rkisp1_info rk3399_isp_info = {
 	.clks = rk3399_isp_clks,
 	.clk_size = ARRAY_SIZE(rk3399_isp_clks),
 	.isrs = rk3399_isp_isrs,
@@ -449,11 +449,11 @@ static const struct rkisp1_match_data rk3399_isp_match_data = {
 static const struct of_device_id rkisp1_of_match[] = {
 	{
 		.compatible = "rockchip,px30-cif-isp",
-		.data = &px30_isp_match_data,
+		.data = &px30_isp_info,
 	},
 	{
 		.compatible = "rockchip,rk3399-cif-isp",
-		.data = &rk3399_isp_match_data,
+		.data = &rk3399_isp_info,
 	},
 	{},
 };
@@ -461,7 +461,7 @@ MODULE_DEVICE_TABLE(of, rkisp1_of_match);
 
 static int rkisp1_probe(struct platform_device *pdev)
 {
-	const struct rkisp1_match_data *match_data;
+	const struct rkisp1_info *info;
 	struct device *dev = &pdev->dev;
 	struct rkisp1_device *rkisp1;
 	struct v4l2_device *v4l2_dev;
@@ -469,8 +469,8 @@ static int rkisp1_probe(struct platform_device *pdev)
 	int ret, irq;
 	u32 cif_id;
 
-	match_data = of_device_get_match_data(&pdev->dev);
-	if (!match_data)
+	info = of_device_get_match_data(&pdev->dev);
+	if (!info)
 		return -ENODEV;
 
 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
@@ -486,14 +486,14 @@ static int rkisp1_probe(struct platform_device *pdev)
 	if (IS_ERR(rkisp1->base_addr))
 		return PTR_ERR(rkisp1->base_addr);
 
-	for (i = 0; i < match_data->isr_size; i++) {
-		irq = match_data->isrs[i].name
-		    ? platform_get_irq_byname(pdev, match_data->isrs[i].name)
+	for (i = 0; i < info->isr_size; i++) {
+		irq = info->isrs[i].name
+		    ? platform_get_irq_byname(pdev, info->isrs[i].name)
 		    : platform_get_irq(pdev, i);
 		if (irq < 0)
 			return irq;
 
-		ret = devm_request_irq(dev, irq, match_data->isrs[i].isr, IRQF_SHARED,
+		ret = devm_request_irq(dev, irq, info->isrs[i].isr, IRQF_SHARED,
 				       dev_driver_string(dev), dev);
 		if (ret) {
 			dev_err(dev, "request irq failed: %d\n", ret);
@@ -501,12 +501,12 @@ static int rkisp1_probe(struct platform_device *pdev)
 		}
 	}
 
-	for (i = 0; i < match_data->clk_size; i++)
-		rkisp1->clks[i].id = match_data->clks[i];
-	ret = devm_clk_bulk_get(dev, match_data->clk_size, rkisp1->clks);
+	for (i = 0; i < info->clk_size; i++)
+		rkisp1->clks[i].id = info->clks[i];
+	ret = devm_clk_bulk_get(dev, info->clk_size, rkisp1->clks);
 	if (ret)
 		return ret;
-	rkisp1->clk_size = match_data->clk_size;
+	rkisp1->clk_size = info->clk_size;
 
 	pm_runtime_enable(&pdev->dev);
 
@@ -519,7 +519,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 
 	pm_runtime_put(&pdev->dev);
 
-	rkisp1->media_dev.hw_revision = match_data->isp_ver;
+	rkisp1->media_dev.hw_revision = info->isp_ver;
 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
 		sizeof(rkisp1->media_dev.model));
 	rkisp1->media_dev.dev = &pdev->dev;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 06/55] media: rkisp1: Rename rkisp1_match_data to rkisp1_info
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1_match_data structure contains device model-specific
information. It it referenced from OF match data, but that's an
implementation detail. Rename it to rkisp1_info to reflect its main
purpose.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 34 +++++++++----------
 1 file changed, 17 insertions(+), 17 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index ba773c0784fb..258980ef4783 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -105,7 +105,7 @@ struct rkisp1_isr_data {
 	irqreturn_t (*isr)(int irq, void *ctx);
 };
 
-struct rkisp1_match_data {
+struct rkisp1_info {
 	const char * const *clks;
 	unsigned int clk_size;
 	const struct rkisp1_isr_data *isrs;
@@ -420,7 +420,7 @@ static const struct rkisp1_isr_data px30_isp_isrs[] = {
 	{ "mipi", rkisp1_mipi_isr },
 };
 
-static const struct rkisp1_match_data px30_isp_match_data = {
+static const struct rkisp1_info px30_isp_info = {
 	.clks = px30_isp_clks,
 	.clk_size = ARRAY_SIZE(px30_isp_clks),
 	.isrs = px30_isp_isrs,
@@ -438,7 +438,7 @@ static const struct rkisp1_isr_data rk3399_isp_isrs[] = {
 	{ NULL, rkisp1_isr },
 };
 
-static const struct rkisp1_match_data rk3399_isp_match_data = {
+static const struct rkisp1_info rk3399_isp_info = {
 	.clks = rk3399_isp_clks,
 	.clk_size = ARRAY_SIZE(rk3399_isp_clks),
 	.isrs = rk3399_isp_isrs,
@@ -449,11 +449,11 @@ static const struct rkisp1_match_data rk3399_isp_match_data = {
 static const struct of_device_id rkisp1_of_match[] = {
 	{
 		.compatible = "rockchip,px30-cif-isp",
-		.data = &px30_isp_match_data,
+		.data = &px30_isp_info,
 	},
 	{
 		.compatible = "rockchip,rk3399-cif-isp",
-		.data = &rk3399_isp_match_data,
+		.data = &rk3399_isp_info,
 	},
 	{},
 };
@@ -461,7 +461,7 @@ MODULE_DEVICE_TABLE(of, rkisp1_of_match);
 
 static int rkisp1_probe(struct platform_device *pdev)
 {
-	const struct rkisp1_match_data *match_data;
+	const struct rkisp1_info *info;
 	struct device *dev = &pdev->dev;
 	struct rkisp1_device *rkisp1;
 	struct v4l2_device *v4l2_dev;
@@ -469,8 +469,8 @@ static int rkisp1_probe(struct platform_device *pdev)
 	int ret, irq;
 	u32 cif_id;
 
-	match_data = of_device_get_match_data(&pdev->dev);
-	if (!match_data)
+	info = of_device_get_match_data(&pdev->dev);
+	if (!info)
 		return -ENODEV;
 
 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
@@ -486,14 +486,14 @@ static int rkisp1_probe(struct platform_device *pdev)
 	if (IS_ERR(rkisp1->base_addr))
 		return PTR_ERR(rkisp1->base_addr);
 
-	for (i = 0; i < match_data->isr_size; i++) {
-		irq = match_data->isrs[i].name
-		    ? platform_get_irq_byname(pdev, match_data->isrs[i].name)
+	for (i = 0; i < info->isr_size; i++) {
+		irq = info->isrs[i].name
+		    ? platform_get_irq_byname(pdev, info->isrs[i].name)
 		    : platform_get_irq(pdev, i);
 		if (irq < 0)
 			return irq;
 
-		ret = devm_request_irq(dev, irq, match_data->isrs[i].isr, IRQF_SHARED,
+		ret = devm_request_irq(dev, irq, info->isrs[i].isr, IRQF_SHARED,
 				       dev_driver_string(dev), dev);
 		if (ret) {
 			dev_err(dev, "request irq failed: %d\n", ret);
@@ -501,12 +501,12 @@ static int rkisp1_probe(struct platform_device *pdev)
 		}
 	}
 
-	for (i = 0; i < match_data->clk_size; i++)
-		rkisp1->clks[i].id = match_data->clks[i];
-	ret = devm_clk_bulk_get(dev, match_data->clk_size, rkisp1->clks);
+	for (i = 0; i < info->clk_size; i++)
+		rkisp1->clks[i].id = info->clks[i];
+	ret = devm_clk_bulk_get(dev, info->clk_size, rkisp1->clks);
 	if (ret)
 		return ret;
-	rkisp1->clk_size = match_data->clk_size;
+	rkisp1->clk_size = info->clk_size;
 
 	pm_runtime_enable(&pdev->dev);
 
@@ -519,7 +519,7 @@ static int rkisp1_probe(struct platform_device *pdev)
 
 	pm_runtime_put(&pdev->dev);
 
-	rkisp1->media_dev.hw_revision = match_data->isp_ver;
+	rkisp1->media_dev.hw_revision = info->isp_ver;
 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
 		sizeof(rkisp1->media_dev.model));
 	rkisp1->media_dev.dev = &pdev->dev;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

To make it possible to use the rkisp1_info after probe time (for
instance to make code conditional on the ISP version), save it in the
main rkisp1_device structure. To achieve this, also move the info
structure into the common header, and document it.

While at it, drop a NULL check in rkisp1_probe() for the match data as
it can't happen.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
 2 files changed, 25 insertions(+), 12 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index a67fe7b1dfa1..50d31a254b03 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
 	RKISP1_ISP_PAD_MAX
 };
 
+/*
+ * struct rkisp1_info - Model-specific ISP Information
+ *
+ * @clks: array of ISP clock names
+ * @clk_size: number of entries in the @clks array
+ * @isrs: array of ISP interrupt descriptors
+ * @isr_size: number of entires in the @isrs array
+ * @isp_ver: ISP version
+ *
+ * This structure contains information about the ISP specific to a particular
+ * ISP model, version, or integration in a particular SoC.
+ */
+struct rkisp1_info {
+	const char * const *clks;
+	unsigned int clk_size;
+	const struct rkisp1_isr_data *isrs;
+	unsigned int isr_size;
+	enum rkisp1_cif_isp_version isp_ver;
+};
+
 /*
  * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
  *				of the v4l2-async API
@@ -395,6 +415,7 @@ struct rkisp1_debug {
  * @pipe:	   media pipeline
  * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
  * @debug:	   debug params to be exposed on debugfs
+ * @info:	   version-specific ISP information
  */
 struct rkisp1_device {
 	void __iomem *base_addr;
@@ -413,6 +434,7 @@ struct rkisp1_device {
 	struct media_pipeline pipe;
 	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
 	struct rkisp1_debug debug;
+	const struct rkisp1_info *info;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 258980ef4783..39ae35074062 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -105,14 +105,6 @@ struct rkisp1_isr_data {
 	irqreturn_t (*isr)(int irq, void *ctx);
 };
 
-struct rkisp1_info {
-	const char * const *clks;
-	unsigned int clk_size;
-	const struct rkisp1_isr_data *isrs;
-	unsigned int isr_size;
-	enum rkisp1_cif_isp_version isp_ver;
-};
-
 /* ----------------------------------------------------------------------------
  * Sensor DT bindings
  */
@@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
 	int ret, irq;
 	u32 cif_id;
 
-	info = of_device_get_match_data(&pdev->dev);
-	if (!info)
-		return -ENODEV;
-
 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
 	if (!rkisp1)
 		return -ENOMEM;
 
+	info = of_device_get_match_data(dev);
+	rkisp1->info = info;
+
 	dev_set_drvdata(dev, rkisp1);
 	rkisp1->dev = dev;
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

To make it possible to use the rkisp1_info after probe time (for
instance to make code conditional on the ISP version), save it in the
main rkisp1_device structure. To achieve this, also move the info
structure into the common header, and document it.

While at it, drop a NULL check in rkisp1_probe() for the match data as
it can't happen.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
 2 files changed, 25 insertions(+), 12 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index a67fe7b1dfa1..50d31a254b03 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
 	RKISP1_ISP_PAD_MAX
 };
 
+/*
+ * struct rkisp1_info - Model-specific ISP Information
+ *
+ * @clks: array of ISP clock names
+ * @clk_size: number of entries in the @clks array
+ * @isrs: array of ISP interrupt descriptors
+ * @isr_size: number of entires in the @isrs array
+ * @isp_ver: ISP version
+ *
+ * This structure contains information about the ISP specific to a particular
+ * ISP model, version, or integration in a particular SoC.
+ */
+struct rkisp1_info {
+	const char * const *clks;
+	unsigned int clk_size;
+	const struct rkisp1_isr_data *isrs;
+	unsigned int isr_size;
+	enum rkisp1_cif_isp_version isp_ver;
+};
+
 /*
  * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
  *				of the v4l2-async API
@@ -395,6 +415,7 @@ struct rkisp1_debug {
  * @pipe:	   media pipeline
  * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
  * @debug:	   debug params to be exposed on debugfs
+ * @info:	   version-specific ISP information
  */
 struct rkisp1_device {
 	void __iomem *base_addr;
@@ -413,6 +434,7 @@ struct rkisp1_device {
 	struct media_pipeline pipe;
 	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
 	struct rkisp1_debug debug;
+	const struct rkisp1_info *info;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 258980ef4783..39ae35074062 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -105,14 +105,6 @@ struct rkisp1_isr_data {
 	irqreturn_t (*isr)(int irq, void *ctx);
 };
 
-struct rkisp1_info {
-	const char * const *clks;
-	unsigned int clk_size;
-	const struct rkisp1_isr_data *isrs;
-	unsigned int isr_size;
-	enum rkisp1_cif_isp_version isp_ver;
-};
-
 /* ----------------------------------------------------------------------------
  * Sensor DT bindings
  */
@@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
 	int ret, irq;
 	u32 cif_id;
 
-	info = of_device_get_match_data(&pdev->dev);
-	if (!info)
-		return -ENODEV;
-
 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
 	if (!rkisp1)
 		return -ENOMEM;
 
+	info = of_device_get_match_data(dev);
+	rkisp1->info = info;
+
 	dev_set_drvdata(dev, rkisp1);
 	rkisp1->dev = dev;
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 08/55] media: rkisp1: Access ISP version from info pointer
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP version is stored in the media_device hw_revision field and
access from there in the driver. Now that we store a pointer to the
match data in the rkisp1_device structure, access the ISP version from
there to make the code clearer and avoid depending on the media_device.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c    | 4 ++--
 drivers/media/platform/rockchip/rkisp1/rkisp1-params.c | 2 +-
 drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c  | 2 +-
 3 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 02968656f3c0..328e8fec14e9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -417,7 +417,7 @@ static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
 	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
 
 	/* V12 could also use a newer csi2-host, but we don't want that yet */
-	if (rkisp1->media_dev.hw_revision == RKISP1_V12)
+	if (rkisp1->info->isp_ver == RKISP1_V12)
 		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
 
 	/* Configure Data Type and Virtual Channel */
@@ -535,7 +535,7 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_ICCL, val);
 
 	/* ensure sp and mp can run at the same time in V12 */
-	if (rkisp1->media_dev.hw_revision == RKISP1_V12) {
+	if (rkisp1->info->isp_ver == RKISP1_V12) {
 		val = RKISP1_CIF_CLK_CTRL_MI_Y12 | RKISP1_CIF_CLK_CTRL_MI_SP |
 		      RKISP1_CIF_CLK_CTRL_MI_RAW0 | RKISP1_CIF_CLK_CTRL_MI_RAW1 |
 		      RKISP1_CIF_CLK_CTRL_MI_READ | RKISP1_CIF_CLK_CTRL_MI_RAWRD |
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
index c88a9c0fa86e..9da7dc1bc690 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
@@ -1801,7 +1801,7 @@ static void rkisp1_init_params(struct rkisp1_params *params)
 	params->vdev_fmt.fmt.meta.buffersize =
 		sizeof(struct rkisp1_params_cfg);
 
-	if (params->rkisp1->media_dev.hw_revision == RKISP1_V12)
+	if (params->rkisp1->info->isp_ver == RKISP1_V12)
 		params->ops = &rkisp1_v12_params_ops;
 	else
 		params->ops = &rkisp1_v10_params_ops;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
index b7ae9166c52f..7d82356b5345 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
@@ -427,7 +427,7 @@ static void rkisp1_init_stats(struct rkisp1_stats *stats)
 	stats->vdev_fmt.fmt.meta.buffersize =
 		sizeof(struct rkisp1_stat_buffer);
 
-	if (stats->rkisp1->media_dev.hw_revision == RKISP1_V12)
+	if (stats->rkisp1->info->isp_ver == RKISP1_V12)
 		stats->ops = &rkisp1_v12_stats_ops;
 	else
 		stats->ops = &rkisp1_v10_stats_ops;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 08/55] media: rkisp1: Access ISP version from info pointer
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP version is stored in the media_device hw_revision field and
access from there in the driver. Now that we store a pointer to the
match data in the rkisp1_device structure, access the ISP version from
there to make the code clearer and avoid depending on the media_device.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c    | 4 ++--
 drivers/media/platform/rockchip/rkisp1/rkisp1-params.c | 2 +-
 drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c  | 2 +-
 3 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 02968656f3c0..328e8fec14e9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -417,7 +417,7 @@ static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
 	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
 
 	/* V12 could also use a newer csi2-host, but we don't want that yet */
-	if (rkisp1->media_dev.hw_revision == RKISP1_V12)
+	if (rkisp1->info->isp_ver == RKISP1_V12)
 		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
 
 	/* Configure Data Type and Virtual Channel */
@@ -535,7 +535,7 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_ICCL, val);
 
 	/* ensure sp and mp can run at the same time in V12 */
-	if (rkisp1->media_dev.hw_revision == RKISP1_V12) {
+	if (rkisp1->info->isp_ver == RKISP1_V12) {
 		val = RKISP1_CIF_CLK_CTRL_MI_Y12 | RKISP1_CIF_CLK_CTRL_MI_SP |
 		      RKISP1_CIF_CLK_CTRL_MI_RAW0 | RKISP1_CIF_CLK_CTRL_MI_RAW1 |
 		      RKISP1_CIF_CLK_CTRL_MI_READ | RKISP1_CIF_CLK_CTRL_MI_RAWRD |
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
index c88a9c0fa86e..9da7dc1bc690 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
@@ -1801,7 +1801,7 @@ static void rkisp1_init_params(struct rkisp1_params *params)
 	params->vdev_fmt.fmt.meta.buffersize =
 		sizeof(struct rkisp1_params_cfg);
 
-	if (params->rkisp1->media_dev.hw_revision == RKISP1_V12)
+	if (params->rkisp1->info->isp_ver == RKISP1_V12)
 		params->ops = &rkisp1_v12_params_ops;
 	else
 		params->ops = &rkisp1_v10_params_ops;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
index b7ae9166c52f..7d82356b5345 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
@@ -427,7 +427,7 @@ static void rkisp1_init_stats(struct rkisp1_stats *stats)
 	stats->vdev_fmt.fmt.meta.buffersize =
 		sizeof(struct rkisp1_stat_buffer);
 
-	if (stats->rkisp1->media_dev.hw_revision == RKISP1_V12)
+	if (stats->rkisp1->info->isp_ver == RKISP1_V12)
 		stats->ops = &rkisp1_v12_stats_ops;
 	else
 		stats->ops = &rkisp1_v10_stats_ops;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The upcoming CSI receiver split from the ISP to a separate source file
will need to be able to access the list of formats supported by the
driver. Move it out of the ISP's header and into the common header, and
add helper functions for accessing it so that the format list doesn't
need to be stored in the header.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 +++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  28 ++-
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 168 ++----------------
 .../platform/rockchip/rkisp1/rkisp1-resizer.c |  14 +-
 .../platform/rockchip/rkisp1/rkisp1-stats.c   |   2 +-
 5 files changed, 193 insertions(+), 167 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
index cf889666e166..bb0ea20118e1 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
@@ -5,10 +5,158 @@
  * Copyright (C) 2019 Collabora, Ltd.
  */
 
+#include <media/mipi-csi2.h>
 #include <media/v4l2-rect.h>
 
 #include "rkisp1-common.h"
 
+static const struct rkisp1_mbus_info rkisp1_formats[] = {
+	{
+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.direction	= RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_RGGB,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_BGGR,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_GBRG,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_GRBG,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_RGGB,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_BGGR,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_GBRG,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_GRBG,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_RGGB,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_BGGR,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_GBRG,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_GRBG,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	},
+};
+
+unsigned int rkisp1_mbus_info_length(void)
+{
+	return ARRAY_SIZE(rkisp1_formats);
+}
+
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index)
+{
+	if (index >= rkisp1_mbus_info_length())
+		return NULL;
+
+	return &rkisp1_formats[index];
+}
+
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code)
+{
+	unsigned int i;
+
+	for (i = 0; i < ARRAY_SIZE(rkisp1_formats); i++) {
+		const struct rkisp1_mbus_info *fmt = &rkisp1_formats[i];
+
+		if (fmt->mbus_code == mbus_code)
+			return fmt;
+	}
+
+	return NULL;
+}
+
 static const struct v4l2_rect rkisp1_sd_min_crop = {
 	.width = RKISP1_ISP_MIN_WIDTH,
 	.height = RKISP1_ISP_MIN_HEIGHT,
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 50d31a254b03..c7d5c57607bd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -26,7 +26,7 @@
 struct dentry;
 
 /*
- * flags on the 'direction' field in struct 'rkisp1_isp_mbus_info' that indicate
+ * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
  * on which pad the media bus format is supported
  */
 #define RKISP1_ISP_SD_SRC			BIT(0)
@@ -150,8 +150,8 @@ struct rkisp1_isp {
 	struct v4l2_subdev sd;
 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
-	const struct rkisp1_isp_mbus_info *sink_fmt;
-	const struct rkisp1_isp_mbus_info *src_fmt;
+	const struct rkisp1_mbus_info *sink_fmt;
+	const struct rkisp1_mbus_info *src_fmt;
 	struct mutex ops_lock; /* serialize the subdevice ops */
 	bool is_dphy_errctrl_disabled;
 	__u32 frame_sequence;
@@ -438,8 +438,8 @@ struct rkisp1_device {
 };
 
 /*
- * struct rkisp1_isp_mbus_info - ISP media bus info, Translates media bus code to hardware
- *				 format values
+ * struct rkisp1_mbus_info - ISP media bus info, Translates media bus code to hardware
+ *			     format values
  *
  * @mbus_code: media bus code
  * @pixel_enc: pixel encoding
@@ -449,7 +449,7 @@ struct rkisp1_device {
  * @bayer_pat: bayer pattern
  * @direction: a bitmask of the flags indicating on which pad the format is supported on
  */
-struct rkisp1_isp_mbus_info {
+struct rkisp1_mbus_info {
 	u32 mbus_code;
 	enum v4l2_pixel_encoding pixel_enc;
 	u32 mipi_dt;
@@ -481,6 +481,18 @@ static inline u32 rkisp1_read(struct rkisp1_device *rkisp1, unsigned int addr)
 int rkisp1_cap_enum_mbus_codes(struct rkisp1_capture *cap,
 			       struct v4l2_subdev_mbus_code_enum *code);
 
+/*
+ * rkisp1_mbus_info_length - Return the number of supported mbus codes
+ */
+unsigned int rkisp1_mbus_info_length(void);
+
+/*
+ * rkisp1_mbus_info_get_by_index - Retrieve the ith supported mbus info
+ *
+ * @index: index of the mbus info to fetch
+ */
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index);
+
 /*
  * rkisp1_sd_adjust_crop_rect - adjust a rectangle to fit into another rectangle.
  *
@@ -500,11 +512,11 @@ void rkisp1_sd_adjust_crop(struct v4l2_rect *crop,
 			   const struct v4l2_mbus_framefmt *bounds);
 
 /*
- * rkisp1_isp_mbus_info - get the isp info of the media bus code
+ * rkisp1_mbus_info_get_by_code - get the isp info of the media bus code
  *
  * @mbus_code: the media bus code
  */
-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code);
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code);
 
 /* rkisp1_params_configure - configure the params when stream starts.
  *			     This function is called by the isp entity upon stream starts.
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 328e8fec14e9..89577119b571 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -15,7 +15,6 @@
 #include <linux/videodev2.h>
 #include <linux/vmalloc.h>
 
-#include <media/mipi-csi2.h>
 #include <media/v4l2-event.h>
 
 #include "rkisp1-common.h"
@@ -56,144 +55,10 @@
  * +---------------------------------------------------------+
  */
 
-static const struct rkisp1_isp_mbus_info rkisp1_isp_formats[] = {
-	{
-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.direction	= RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_RGGB,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_BGGR,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_GBRG,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_GRBG,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_RGGB,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_BGGR,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_GBRG,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_GRBG,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_RGGB,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_BGGR,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_GBRG,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_GRBG,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	},
-};
-
 /* ----------------------------------------------------------------------------
  * Helpers
  */
 
-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code)
-{
-	unsigned int i;
-
-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
-
-		if (fmt->mbus_code == mbus_code)
-			return fmt;
-	}
-
-	return NULL;
-}
-
 static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
 {
 	struct media_pad *local, *remote;
@@ -275,7 +140,7 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
 static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 {
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
-	const struct rkisp1_isp_mbus_info *src_fmt, *sink_fmt;
+	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct rkisp1_sensor_async *sensor;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
@@ -376,7 +241,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 
 static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 {
-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
 	u32 val, input_sel;
 
 	switch (sink_fmt->bus_width) {
@@ -402,7 +267,7 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 
 static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
 {
-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
 	unsigned int lanes = rkisp1->active_sensor->lanes;
 	u32 mipi_ctrl;
 
@@ -593,11 +458,12 @@ static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
 		return 0;
 	}
 
-	if (code->index >= ARRAY_SIZE(rkisp1_isp_formats))
+	if (code->index >= rkisp1_mbus_info_length())
 		return -EINVAL;
 
-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
+		const struct rkisp1_mbus_info *fmt =
+			rkisp1_mbus_info_get_by_index(i);
 
 		if (fmt->direction & dir)
 			pos++;
@@ -619,7 +485,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
 				      struct v4l2_subdev_state *sd_state,
 				      struct v4l2_subdev_frame_size_enum *fse)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 
 	if (fse->pad == RKISP1_ISP_PAD_SINK_PARAMS ||
 	    fse->pad == RKISP1_ISP_PAD_SOURCE_STATS)
@@ -628,7 +494,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
 	if (fse->index > 0)
 		return -EINVAL;
 
-	mbus_info = rkisp1_isp_mbus_info_get(fse->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(fse->code);
 	if (!mbus_info)
 		return -EINVAL;
 
@@ -695,7 +561,7 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
 				   struct v4l2_mbus_framefmt *format,
 				   unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *src_fmt;
 	const struct v4l2_rect *src_crop;
 
@@ -705,10 +571,10 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
 					   RKISP1_ISP_PAD_SOURCE_VIDEO, which);
 
 	src_fmt->code = format->code;
-	mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
 		src_fmt->code = RKISP1_DEF_SRC_PAD_FMT;
-		mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
+		mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
 	}
 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
 		isp->src_fmt = mbus_info;
@@ -793,7 +659,7 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
 				    struct v4l2_mbus_framefmt *format,
 				    unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *sink_fmt;
 	struct v4l2_rect *sink_crop;
 
@@ -801,10 +667,10 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
 					  which);
 	sink_fmt->code = format->code;
-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
 		sink_fmt->code = RKISP1_DEF_SINK_PAD_FMT;
-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	}
 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
 		isp->sink_fmt = mbus_info;
@@ -1080,8 +946,8 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
 	pads[RKISP1_ISP_PAD_SOURCE_VIDEO].flags = MEDIA_PAD_FL_SOURCE;
 	pads[RKISP1_ISP_PAD_SOURCE_STATS].flags = MEDIA_PAD_FL_SOURCE;
 
-	isp->sink_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SINK_PAD_FMT);
-	isp->src_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SRC_PAD_FMT);
+	isp->sink_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SINK_PAD_FMT);
+	isp->src_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SRC_PAD_FMT);
 
 	mutex_init(&isp->ops_lock);
 	ret = media_entity_pads_init(&sd->entity, RKISP1_ISP_PAD_MAX, pads);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
index 1c07985c810d..f4caa8f684aa 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
@@ -433,14 +433,14 @@ static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
 				   struct v4l2_mbus_framefmt *format,
 				   unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *sink_mbus_info;
+	const struct rkisp1_mbus_info *sink_mbus_info;
 	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
 
 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
 					  which);
 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
 					 which);
-	sink_mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 
 	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
 	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
@@ -462,7 +462,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
 				     struct v4l2_rect *r,
 				     unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *sink_fmt;
 	struct v4l2_rect *sink_crop;
 
@@ -473,7 +473,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
 					    which);
 
 	/* Not crop for MP bayer raw data */
-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 
 	if (rsz->id == RKISP1_MAINPATH &&
 	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
@@ -500,7 +500,7 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
 				    struct v4l2_mbus_framefmt *format,
 				    unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
 	struct v4l2_rect *sink_crop;
 
@@ -516,10 +516,10 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
 	else
 		sink_fmt->code = format->code;
 
-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
 		sink_fmt->code = RKISP1_DEF_FMT;
-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	}
 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
 		rsz->pixel_enc = mbus_info->pixel_enc;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
index 7d82356b5345..2795eef91bdd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
@@ -305,7 +305,7 @@ static void rkisp1_stats_get_bls_meas(struct rkisp1_stats *stats,
 				      struct rkisp1_stat_buffer *pbuf)
 {
 	struct rkisp1_device *rkisp1 = stats->rkisp1;
-	const struct rkisp1_isp_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
+	const struct rkisp1_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
 	struct rkisp1_cif_isp_bls_meas_val *bls_val;
 
 	bls_val = &pbuf->params.ae.bls_val;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The upcoming CSI receiver split from the ISP to a separate source file
will need to be able to access the list of formats supported by the
driver. Move it out of the ISP's header and into the common header, and
add helper functions for accessing it so that the format list doesn't
need to be stored in the header.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 +++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  28 ++-
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 168 ++----------------
 .../platform/rockchip/rkisp1/rkisp1-resizer.c |  14 +-
 .../platform/rockchip/rkisp1/rkisp1-stats.c   |   2 +-
 5 files changed, 193 insertions(+), 167 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
index cf889666e166..bb0ea20118e1 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
@@ -5,10 +5,158 @@
  * Copyright (C) 2019 Collabora, Ltd.
  */
 
+#include <media/mipi-csi2.h>
 #include <media/v4l2-rect.h>
 
 #include "rkisp1-common.h"
 
+static const struct rkisp1_mbus_info rkisp1_formats[] = {
+	{
+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.direction	= RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_RGGB,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_BGGR,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_GBRG,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
+		.bayer_pat	= RKISP1_RAW_GRBG,
+		.bus_width	= 10,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_RGGB,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_BGGR,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_GBRG,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
+		.bayer_pat	= RKISP1_RAW_GRBG,
+		.bus_width	= 12,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_RGGB,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_BGGR,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_GBRG,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
+		.bayer_pat	= RKISP1_RAW_GRBG,
+		.bus_width	= 8,
+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	}, {
+		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
+		.bus_width	= 16,
+		.direction	= RKISP1_ISP_SD_SINK,
+	},
+};
+
+unsigned int rkisp1_mbus_info_length(void)
+{
+	return ARRAY_SIZE(rkisp1_formats);
+}
+
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index)
+{
+	if (index >= rkisp1_mbus_info_length())
+		return NULL;
+
+	return &rkisp1_formats[index];
+}
+
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code)
+{
+	unsigned int i;
+
+	for (i = 0; i < ARRAY_SIZE(rkisp1_formats); i++) {
+		const struct rkisp1_mbus_info *fmt = &rkisp1_formats[i];
+
+		if (fmt->mbus_code == mbus_code)
+			return fmt;
+	}
+
+	return NULL;
+}
+
 static const struct v4l2_rect rkisp1_sd_min_crop = {
 	.width = RKISP1_ISP_MIN_WIDTH,
 	.height = RKISP1_ISP_MIN_HEIGHT,
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 50d31a254b03..c7d5c57607bd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -26,7 +26,7 @@
 struct dentry;
 
 /*
- * flags on the 'direction' field in struct 'rkisp1_isp_mbus_info' that indicate
+ * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
  * on which pad the media bus format is supported
  */
 #define RKISP1_ISP_SD_SRC			BIT(0)
@@ -150,8 +150,8 @@ struct rkisp1_isp {
 	struct v4l2_subdev sd;
 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
-	const struct rkisp1_isp_mbus_info *sink_fmt;
-	const struct rkisp1_isp_mbus_info *src_fmt;
+	const struct rkisp1_mbus_info *sink_fmt;
+	const struct rkisp1_mbus_info *src_fmt;
 	struct mutex ops_lock; /* serialize the subdevice ops */
 	bool is_dphy_errctrl_disabled;
 	__u32 frame_sequence;
@@ -438,8 +438,8 @@ struct rkisp1_device {
 };
 
 /*
- * struct rkisp1_isp_mbus_info - ISP media bus info, Translates media bus code to hardware
- *				 format values
+ * struct rkisp1_mbus_info - ISP media bus info, Translates media bus code to hardware
+ *			     format values
  *
  * @mbus_code: media bus code
  * @pixel_enc: pixel encoding
@@ -449,7 +449,7 @@ struct rkisp1_device {
  * @bayer_pat: bayer pattern
  * @direction: a bitmask of the flags indicating on which pad the format is supported on
  */
-struct rkisp1_isp_mbus_info {
+struct rkisp1_mbus_info {
 	u32 mbus_code;
 	enum v4l2_pixel_encoding pixel_enc;
 	u32 mipi_dt;
@@ -481,6 +481,18 @@ static inline u32 rkisp1_read(struct rkisp1_device *rkisp1, unsigned int addr)
 int rkisp1_cap_enum_mbus_codes(struct rkisp1_capture *cap,
 			       struct v4l2_subdev_mbus_code_enum *code);
 
+/*
+ * rkisp1_mbus_info_length - Return the number of supported mbus codes
+ */
+unsigned int rkisp1_mbus_info_length(void);
+
+/*
+ * rkisp1_mbus_info_get_by_index - Retrieve the ith supported mbus info
+ *
+ * @index: index of the mbus info to fetch
+ */
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index);
+
 /*
  * rkisp1_sd_adjust_crop_rect - adjust a rectangle to fit into another rectangle.
  *
@@ -500,11 +512,11 @@ void rkisp1_sd_adjust_crop(struct v4l2_rect *crop,
 			   const struct v4l2_mbus_framefmt *bounds);
 
 /*
- * rkisp1_isp_mbus_info - get the isp info of the media bus code
+ * rkisp1_mbus_info_get_by_code - get the isp info of the media bus code
  *
  * @mbus_code: the media bus code
  */
-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code);
+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code);
 
 /* rkisp1_params_configure - configure the params when stream starts.
  *			     This function is called by the isp entity upon stream starts.
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 328e8fec14e9..89577119b571 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -15,7 +15,6 @@
 #include <linux/videodev2.h>
 #include <linux/vmalloc.h>
 
-#include <media/mipi-csi2.h>
 #include <media/v4l2-event.h>
 
 #include "rkisp1-common.h"
@@ -56,144 +55,10 @@
  * +---------------------------------------------------------+
  */
 
-static const struct rkisp1_isp_mbus_info rkisp1_isp_formats[] = {
-	{
-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.direction	= RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_RGGB,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_BGGR,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_GBRG,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
-		.bayer_pat	= RKISP1_RAW_GRBG,
-		.bus_width	= 10,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_RGGB,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_BGGR,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_GBRG,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
-		.bayer_pat	= RKISP1_RAW_GRBG,
-		.bus_width	= 12,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_RGGB,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_BGGR,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_GBRG,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
-		.bayer_pat	= RKISP1_RAW_GRBG,
-		.bus_width	= 8,
-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	}, {
-		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
-		.bus_width	= 16,
-		.direction	= RKISP1_ISP_SD_SINK,
-	},
-};
-
 /* ----------------------------------------------------------------------------
  * Helpers
  */
 
-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code)
-{
-	unsigned int i;
-
-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
-
-		if (fmt->mbus_code == mbus_code)
-			return fmt;
-	}
-
-	return NULL;
-}
-
 static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
 {
 	struct media_pad *local, *remote;
@@ -275,7 +140,7 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
 static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 {
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
-	const struct rkisp1_isp_mbus_info *src_fmt, *sink_fmt;
+	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct rkisp1_sensor_async *sensor;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
@@ -376,7 +241,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 
 static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 {
-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
 	u32 val, input_sel;
 
 	switch (sink_fmt->bus_width) {
@@ -402,7 +267,7 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 
 static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
 {
-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
 	unsigned int lanes = rkisp1->active_sensor->lanes;
 	u32 mipi_ctrl;
 
@@ -593,11 +458,12 @@ static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
 		return 0;
 	}
 
-	if (code->index >= ARRAY_SIZE(rkisp1_isp_formats))
+	if (code->index >= rkisp1_mbus_info_length())
 		return -EINVAL;
 
-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
+		const struct rkisp1_mbus_info *fmt =
+			rkisp1_mbus_info_get_by_index(i);
 
 		if (fmt->direction & dir)
 			pos++;
@@ -619,7 +485,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
 				      struct v4l2_subdev_state *sd_state,
 				      struct v4l2_subdev_frame_size_enum *fse)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 
 	if (fse->pad == RKISP1_ISP_PAD_SINK_PARAMS ||
 	    fse->pad == RKISP1_ISP_PAD_SOURCE_STATS)
@@ -628,7 +494,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
 	if (fse->index > 0)
 		return -EINVAL;
 
-	mbus_info = rkisp1_isp_mbus_info_get(fse->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(fse->code);
 	if (!mbus_info)
 		return -EINVAL;
 
@@ -695,7 +561,7 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
 				   struct v4l2_mbus_framefmt *format,
 				   unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *src_fmt;
 	const struct v4l2_rect *src_crop;
 
@@ -705,10 +571,10 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
 					   RKISP1_ISP_PAD_SOURCE_VIDEO, which);
 
 	src_fmt->code = format->code;
-	mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
 		src_fmt->code = RKISP1_DEF_SRC_PAD_FMT;
-		mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
+		mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
 	}
 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
 		isp->src_fmt = mbus_info;
@@ -793,7 +659,7 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
 				    struct v4l2_mbus_framefmt *format,
 				    unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *sink_fmt;
 	struct v4l2_rect *sink_crop;
 
@@ -801,10 +667,10 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
 					  which);
 	sink_fmt->code = format->code;
-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
 		sink_fmt->code = RKISP1_DEF_SINK_PAD_FMT;
-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	}
 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
 		isp->sink_fmt = mbus_info;
@@ -1080,8 +946,8 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
 	pads[RKISP1_ISP_PAD_SOURCE_VIDEO].flags = MEDIA_PAD_FL_SOURCE;
 	pads[RKISP1_ISP_PAD_SOURCE_STATS].flags = MEDIA_PAD_FL_SOURCE;
 
-	isp->sink_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SINK_PAD_FMT);
-	isp->src_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SRC_PAD_FMT);
+	isp->sink_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SINK_PAD_FMT);
+	isp->src_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SRC_PAD_FMT);
 
 	mutex_init(&isp->ops_lock);
 	ret = media_entity_pads_init(&sd->entity, RKISP1_ISP_PAD_MAX, pads);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
index 1c07985c810d..f4caa8f684aa 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
@@ -433,14 +433,14 @@ static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
 				   struct v4l2_mbus_framefmt *format,
 				   unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *sink_mbus_info;
+	const struct rkisp1_mbus_info *sink_mbus_info;
 	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
 
 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
 					  which);
 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
 					 which);
-	sink_mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 
 	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
 	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
@@ -462,7 +462,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
 				     struct v4l2_rect *r,
 				     unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *sink_fmt;
 	struct v4l2_rect *sink_crop;
 
@@ -473,7 +473,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
 					    which);
 
 	/* Not crop for MP bayer raw data */
-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 
 	if (rsz->id == RKISP1_MAINPATH &&
 	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
@@ -500,7 +500,7 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
 				    struct v4l2_mbus_framefmt *format,
 				    unsigned int which)
 {
-	const struct rkisp1_isp_mbus_info *mbus_info;
+	const struct rkisp1_mbus_info *mbus_info;
 	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
 	struct v4l2_rect *sink_crop;
 
@@ -516,10 +516,10 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
 	else
 		sink_fmt->code = format->code;
 
-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
 		sink_fmt->code = RKISP1_DEF_FMT;
-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
 	}
 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
 		rsz->pixel_enc = mbus_info->pixel_enc;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
index 7d82356b5345..2795eef91bdd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
@@ -305,7 +305,7 @@ static void rkisp1_stats_get_bls_meas(struct rkisp1_stats *stats,
 				      struct rkisp1_stat_buffer *pbuf)
 {
 	struct rkisp1_device *rkisp1 = stats->rkisp1;
-	const struct rkisp1_isp_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
+	const struct rkisp1_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
 	struct rkisp1_cif_isp_bls_meas_val *bls_val;
 
 	bls_val = &pbuf->params.ae.bls_val;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

When a link validation failure occurs, print a debug message to help
diagnosing the cause.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 94819e6c23e2..94a0d787a312 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct media_link *link)
 
 	if (sd_fmt.format.height != cap->pix.fmt.height ||
 	    sd_fmt.format.width != cap->pix.fmt.width ||
-	    sd_fmt.format.code != fmt->mbus)
+	    sd_fmt.format.code != fmt->mbus) {
+		dev_dbg(cap->rkisp1->dev,
+			"link '%s':%u -> '%s':%u not valid: 0x%04x/%ux%u != 0x%04x/%ux%u",
+			link->source->entity->name, link->source->index,
+			link->sink->entity->name, link->sink->index,
+			sd_fmt.format.code, sd_fmt.format.width,
+			sd_fmt.format.height, fmt->mbus, cap->pix.fmt.width,
+			cap->pix.fmt.height);
 		return -EPIPE;
+	}
 
 	return 0;
 }
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

When a link validation failure occurs, print a debug message to help
diagnosing the cause.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 94819e6c23e2..94a0d787a312 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct media_link *link)
 
 	if (sd_fmt.format.height != cap->pix.fmt.height ||
 	    sd_fmt.format.width != cap->pix.fmt.width ||
-	    sd_fmt.format.code != fmt->mbus)
+	    sd_fmt.format.code != fmt->mbus) {
+		dev_dbg(cap->rkisp1->dev,
+			"link '%s':%u -> '%s':%u not valid: 0x%04x/%ux%u != 0x%04x/%ux%u",
+			link->source->entity->name, link->source->index,
+			link->sink->entity->name, link->sink->index,
+			sd_fmt.format.code, sd_fmt.format.width,
+			sd_fmt.format.height, fmt->mbus, cap->pix.fmt.width,
+			cap->pix.fmt.height);
 		return -EPIPE;
+	}
 
 	return 0;
 }
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 11/55] media: rkisp1: Move sensor .s_stream() call to ISP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Move the calls to the active sensor's .s_stream() operation to the ISP
subdev's .s_stream(). This groups all handling of the active sensor in
one place, preparing for a rework of that code.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-capture.c  | 12 +-----------
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c  | 11 +++++++++++
 2 files changed, 12 insertions(+), 11 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 94a0d787a312..9edaa95fa44c 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -926,11 +926,8 @@ static void rkisp1_pipeline_stream_disable(struct rkisp1_capture *cap)
 	 * If the other capture is streaming, isp and sensor nodes shouldn't
 	 * be disabled, skip them.
 	 */
-	if (rkisp1->pipe.streaming_count < 2) {
-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-				 false);
+	if (rkisp1->pipe.streaming_count < 2)
 		v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
-	}
 
 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
 			 false);
@@ -966,15 +963,8 @@ static int rkisp1_pipeline_stream_enable(struct rkisp1_capture *cap)
 	if (ret)
 		goto err_disable_rsz;
 
-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-			       true);
-	if (ret)
-		goto err_disable_isp;
-
 	return 0;
 
-err_disable_isp:
-	v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
 err_disable_rsz:
 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
 			 false);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 89577119b571..58cf6d21f1eb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -857,6 +857,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	int ret = 0;
 
 	if (!enable) {
+		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
+				 false);
+
 		rkisp1_isp_stop(rkisp1);
 		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
 		return 0;
@@ -886,6 +889,14 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 
 	rkisp1_isp_start(rkisp1);
 
+	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
+			       true);
+	if (ret) {
+		rkisp1_isp_stop(rkisp1);
+		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
+		goto mutex_unlock;
+	}
+
 mutex_unlock:
 	mutex_unlock(&isp->ops_lock);
 	return ret;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 11/55] media: rkisp1: Move sensor .s_stream() call to ISP
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Move the calls to the active sensor's .s_stream() operation to the ISP
subdev's .s_stream(). This groups all handling of the active sensor in
one place, preparing for a rework of that code.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-capture.c  | 12 +-----------
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c  | 11 +++++++++++
 2 files changed, 12 insertions(+), 11 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 94a0d787a312..9edaa95fa44c 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -926,11 +926,8 @@ static void rkisp1_pipeline_stream_disable(struct rkisp1_capture *cap)
 	 * If the other capture is streaming, isp and sensor nodes shouldn't
 	 * be disabled, skip them.
 	 */
-	if (rkisp1->pipe.streaming_count < 2) {
-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-				 false);
+	if (rkisp1->pipe.streaming_count < 2)
 		v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
-	}
 
 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
 			 false);
@@ -966,15 +963,8 @@ static int rkisp1_pipeline_stream_enable(struct rkisp1_capture *cap)
 	if (ret)
 		goto err_disable_rsz;
 
-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-			       true);
-	if (ret)
-		goto err_disable_isp;
-
 	return 0;
 
-err_disable_isp:
-	v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
 err_disable_rsz:
 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
 			 false);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 89577119b571..58cf6d21f1eb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -857,6 +857,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	int ret = 0;
 
 	if (!enable) {
+		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
+				 false);
+
 		rkisp1_isp_stop(rkisp1);
 		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
 		return 0;
@@ -886,6 +889,14 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 
 	rkisp1_isp_start(rkisp1);
 
+	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
+			       true);
+	if (ret) {
+		rkisp1_isp_stop(rkisp1);
+		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
+		goto mutex_unlock;
+	}
+
 mutex_unlock:
 	mutex_unlock(&isp->ops_lock);
 	return ret;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 12/55] media: rkisp1: Reject sensors without pixel rate control at bound time
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1 driver requires the sensor to implement the pixel rate
control. Trying to operate without it will cause an error when starting
streaming. Catch the issue earlier, at bound time.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 6 ++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 -----
 2 files changed, 6 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 39ae35074062..7fc617d51f44 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -190,6 +190,12 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 
 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
 						V4L2_CID_PIXEL_RATE);
+	if (!s_asd->pixel_rate_ctrl) {
+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
+			sd->name);
+		return -EINVAL;
+	}
+
 	s_asd->sd = sd;
 	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
 	if (IS_ERR(s_asd->dphy)) {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 58cf6d21f1eb..81138c676ac0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -823,11 +823,6 @@ static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
 	s64 pixel_clock;
 
-	if (!sensor->pixel_rate_ctrl) {
-		dev_warn(rkisp1->dev, "No pixel rate control in sensor subdev\n");
-		return -EPIPE;
-	}
-
 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
 	if (!pixel_clock) {
 		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 12/55] media: rkisp1: Reject sensors without pixel rate control at bound time
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1 driver requires the sensor to implement the pixel rate
control. Trying to operate without it will cause an error when starting
streaming. Catch the issue earlier, at bound time.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 6 ++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 -----
 2 files changed, 6 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 39ae35074062..7fc617d51f44 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -190,6 +190,12 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 
 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
 						V4L2_CID_PIXEL_RATE);
+	if (!s_asd->pixel_rate_ctrl) {
+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
+			sd->name);
+		return -EINVAL;
+	}
+
 	s_asd->sd = sd;
 	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
 	if (IS_ERR(s_asd->dphy)) {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 58cf6d21f1eb..81138c676ac0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -823,11 +823,6 @@ static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
 	s64 pixel_clock;
 
-	if (!sensor->pixel_rate_ctrl) {
-		dev_warn(rkisp1->dev, "No pixel rate control in sensor subdev\n");
-		return -EPIPE;
-	}
-
 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
 	if (!pixel_clock) {
 		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 13/55] media: rkisp1: Create link from sensor to ISP at notifier bound time
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Links from sensors to the ISP can be created as sensors are bound. Move
the link creation from rkisp1_create_links() to the bound notifier, and
clean up the rkisp1_create_links() function while at it.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 87 ++++++++-----------
 2 files changed, 40 insertions(+), 49 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index c7d5c57607bd..ba11baf75fa9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -116,6 +116,7 @@ struct rkisp1_info {
  *				of the v4l2-async API
  *
  * @asd:		async_subdev variable for the sensor
+ * @index:		index of the sensor (counting sensor found in DT)
  * @lanes:		number of lanes
  * @mbus_type:		type of bus (currently only CSI2 is supported)
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
@@ -125,6 +126,7 @@ struct rkisp1_info {
  */
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
+	unsigned int index;
 	unsigned int lanes;
 	enum v4l2_mbus_type mbus_type;
 	unsigned int mbus_flags;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 7fc617d51f44..4501aea265cb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -111,72 +111,46 @@ struct rkisp1_isr_data {
 
 static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 {
-	struct media_entity *source, *sink;
-	unsigned int flags, source_pad;
-	struct v4l2_subdev *sd;
 	unsigned int i;
 	int ret;
 
-	/* sensor links */
-	flags = MEDIA_LNK_FL_ENABLED;
-	list_for_each_entry(sd, &rkisp1->v4l2_dev.subdevs, list) {
-		if (sd == &rkisp1->isp.sd ||
-		    sd == &rkisp1->resizer_devs[RKISP1_MAINPATH].sd ||
-		    sd == &rkisp1->resizer_devs[RKISP1_SELFPATH].sd)
-			continue;
-
-		ret = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
-						  MEDIA_PAD_FL_SOURCE);
-		if (ret < 0) {
-			dev_err(rkisp1->dev, "failed to find src pad for %s\n",
-				sd->name);
-			return ret;
-		}
-		source_pad = ret;
-
-		ret = media_create_pad_link(&sd->entity, source_pad,
-					    &rkisp1->isp.sd.entity,
-					    RKISP1_ISP_PAD_SINK_VIDEO,
-					    flags);
-		if (ret)
-			return ret;
-
-		flags = 0;
-	}
-
-	flags = MEDIA_LNK_FL_ENABLED | MEDIA_LNK_FL_IMMUTABLE;
-
 	/* create ISP->RSZ->CAP links */
 	for (i = 0; i < 2; i++) {
-		source = &rkisp1->isp.sd.entity;
-		sink = &rkisp1->resizer_devs[i].sd.entity;
-		ret = media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_VIDEO,
-					    sink, RKISP1_RSZ_PAD_SINK,
+		struct media_entity *resizer =
+			&rkisp1->resizer_devs[i].sd.entity;
+		struct media_entity *capture =
+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
+
+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
+					    resizer, RKISP1_RSZ_PAD_SINK,
 					    MEDIA_LNK_FL_ENABLED);
 		if (ret)
 			return ret;
 
-		source = sink;
-		sink = &rkisp1->capture_devs[i].vnode.vdev.entity;
-		ret = media_create_pad_link(source, RKISP1_RSZ_PAD_SRC,
-					    sink, 0, flags);
+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
+					    capture, 0,
+					    MEDIA_LNK_FL_ENABLED |
+					    MEDIA_LNK_FL_IMMUTABLE);
 		if (ret)
 			return ret;
 	}
 
 	/* params links */
-	source = &rkisp1->params.vnode.vdev.entity;
-	sink = &rkisp1->isp.sd.entity;
-	ret = media_create_pad_link(source, 0, sink,
-				    RKISP1_ISP_PAD_SINK_PARAMS, flags);
+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_PARAMS,
+				    MEDIA_LNK_FL_ENABLED |
+				    MEDIA_LNK_FL_IMMUTABLE);
 	if (ret)
 		return ret;
 
 	/* 3A stats links */
-	source = &rkisp1->isp.sd.entity;
-	sink = &rkisp1->stats.vnode.vdev.entity;
-	return media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_STATS,
-				     sink, 0, flags);
+	return media_create_pad_link(&rkisp1->isp.sd.entity,
+				     RKISP1_ISP_PAD_SOURCE_STATS,
+				     &rkisp1->stats.vnode.vdev.entity, 0,
+				     MEDIA_LNK_FL_ENABLED |
+				     MEDIA_LNK_FL_IMMUTABLE);
 }
 
 static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
@@ -187,6 +161,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		container_of(notifier, struct rkisp1_device, notifier);
 	struct rkisp1_sensor_async *s_asd =
 		container_of(asd, struct rkisp1_sensor_async, asd);
+	int source_pad;
 
 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
 						V4L2_CID_PIXEL_RATE);
@@ -206,7 +181,19 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 
 	phy_init(s_asd->dphy);
 
-	return 0;
+	/* Create the link to the sensor. */
+	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
+						 MEDIA_PAD_FL_SOURCE);
+	if (source_pad < 0) {
+		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
+			sd->name);
+		return source_pad;
+	}
+
+	return media_create_pad_link(&sd->entity, source_pad,
+				     &rkisp1->isp.sd.entity,
+				     RKISP1_ISP_PAD_SINK_VIDEO,
+				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
 }
 
 static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
@@ -248,6 +235,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
 	unsigned int next_id = 0;
+	unsigned int index = 0;
 	int ret;
 
 	v4l2_async_nf_init(ntf);
@@ -277,6 +265,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
 			goto err_parse;
 		}
 
+		rk_asd->index = index++;
 		rk_asd->mbus_type = vep.bus_type;
 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 13/55] media: rkisp1: Create link from sensor to ISP at notifier bound time
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Links from sensors to the ISP can be created as sensors are bound. Move
the link creation from rkisp1_create_links() to the bound notifier, and
clean up the rkisp1_create_links() function while at it.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 87 ++++++++-----------
 2 files changed, 40 insertions(+), 49 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index c7d5c57607bd..ba11baf75fa9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -116,6 +116,7 @@ struct rkisp1_info {
  *				of the v4l2-async API
  *
  * @asd:		async_subdev variable for the sensor
+ * @index:		index of the sensor (counting sensor found in DT)
  * @lanes:		number of lanes
  * @mbus_type:		type of bus (currently only CSI2 is supported)
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
@@ -125,6 +126,7 @@ struct rkisp1_info {
  */
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
+	unsigned int index;
 	unsigned int lanes;
 	enum v4l2_mbus_type mbus_type;
 	unsigned int mbus_flags;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 7fc617d51f44..4501aea265cb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -111,72 +111,46 @@ struct rkisp1_isr_data {
 
 static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 {
-	struct media_entity *source, *sink;
-	unsigned int flags, source_pad;
-	struct v4l2_subdev *sd;
 	unsigned int i;
 	int ret;
 
-	/* sensor links */
-	flags = MEDIA_LNK_FL_ENABLED;
-	list_for_each_entry(sd, &rkisp1->v4l2_dev.subdevs, list) {
-		if (sd == &rkisp1->isp.sd ||
-		    sd == &rkisp1->resizer_devs[RKISP1_MAINPATH].sd ||
-		    sd == &rkisp1->resizer_devs[RKISP1_SELFPATH].sd)
-			continue;
-
-		ret = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
-						  MEDIA_PAD_FL_SOURCE);
-		if (ret < 0) {
-			dev_err(rkisp1->dev, "failed to find src pad for %s\n",
-				sd->name);
-			return ret;
-		}
-		source_pad = ret;
-
-		ret = media_create_pad_link(&sd->entity, source_pad,
-					    &rkisp1->isp.sd.entity,
-					    RKISP1_ISP_PAD_SINK_VIDEO,
-					    flags);
-		if (ret)
-			return ret;
-
-		flags = 0;
-	}
-
-	flags = MEDIA_LNK_FL_ENABLED | MEDIA_LNK_FL_IMMUTABLE;
-
 	/* create ISP->RSZ->CAP links */
 	for (i = 0; i < 2; i++) {
-		source = &rkisp1->isp.sd.entity;
-		sink = &rkisp1->resizer_devs[i].sd.entity;
-		ret = media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_VIDEO,
-					    sink, RKISP1_RSZ_PAD_SINK,
+		struct media_entity *resizer =
+			&rkisp1->resizer_devs[i].sd.entity;
+		struct media_entity *capture =
+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
+
+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
+					    resizer, RKISP1_RSZ_PAD_SINK,
 					    MEDIA_LNK_FL_ENABLED);
 		if (ret)
 			return ret;
 
-		source = sink;
-		sink = &rkisp1->capture_devs[i].vnode.vdev.entity;
-		ret = media_create_pad_link(source, RKISP1_RSZ_PAD_SRC,
-					    sink, 0, flags);
+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
+					    capture, 0,
+					    MEDIA_LNK_FL_ENABLED |
+					    MEDIA_LNK_FL_IMMUTABLE);
 		if (ret)
 			return ret;
 	}
 
 	/* params links */
-	source = &rkisp1->params.vnode.vdev.entity;
-	sink = &rkisp1->isp.sd.entity;
-	ret = media_create_pad_link(source, 0, sink,
-				    RKISP1_ISP_PAD_SINK_PARAMS, flags);
+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_PARAMS,
+				    MEDIA_LNK_FL_ENABLED |
+				    MEDIA_LNK_FL_IMMUTABLE);
 	if (ret)
 		return ret;
 
 	/* 3A stats links */
-	source = &rkisp1->isp.sd.entity;
-	sink = &rkisp1->stats.vnode.vdev.entity;
-	return media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_STATS,
-				     sink, 0, flags);
+	return media_create_pad_link(&rkisp1->isp.sd.entity,
+				     RKISP1_ISP_PAD_SOURCE_STATS,
+				     &rkisp1->stats.vnode.vdev.entity, 0,
+				     MEDIA_LNK_FL_ENABLED |
+				     MEDIA_LNK_FL_IMMUTABLE);
 }
 
 static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
@@ -187,6 +161,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		container_of(notifier, struct rkisp1_device, notifier);
 	struct rkisp1_sensor_async *s_asd =
 		container_of(asd, struct rkisp1_sensor_async, asd);
+	int source_pad;
 
 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
 						V4L2_CID_PIXEL_RATE);
@@ -206,7 +181,19 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 
 	phy_init(s_asd->dphy);
 
-	return 0;
+	/* Create the link to the sensor. */
+	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
+						 MEDIA_PAD_FL_SOURCE);
+	if (source_pad < 0) {
+		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
+			sd->name);
+		return source_pad;
+	}
+
+	return media_create_pad_link(&sd->entity, source_pad,
+				     &rkisp1->isp.sd.entity,
+				     RKISP1_ISP_PAD_SINK_VIDEO,
+				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
 }
 
 static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
@@ -248,6 +235,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
 	unsigned int next_id = 0;
+	unsigned int index = 0;
 	int ret;
 
 	v4l2_async_nf_init(ntf);
@@ -277,6 +265,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
 			goto err_parse;
 		}
 
+		rk_asd->index = index++;
 		rk_asd->mbus_type = vep.bus_type;
 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 14/55] media: rkisp1: Create internal links at probe time
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

There's no need to wait until all async subdevs are bound before
creating internal links. Create them at probe time.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 105 ++++++++----------
 1 file changed, 49 insertions(+), 56 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 4501aea265cb..7bb1235cddea 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -109,50 +109,6 @@ struct rkisp1_isr_data {
  * Sensor DT bindings
  */
 
-static int rkisp1_create_links(struct rkisp1_device *rkisp1)
-{
-	unsigned int i;
-	int ret;
-
-	/* create ISP->RSZ->CAP links */
-	for (i = 0; i < 2; i++) {
-		struct media_entity *resizer =
-			&rkisp1->resizer_devs[i].sd.entity;
-		struct media_entity *capture =
-			&rkisp1->capture_devs[i].vnode.vdev.entity;;
-
-		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
-					    RKISP1_ISP_PAD_SOURCE_VIDEO,
-					    resizer, RKISP1_RSZ_PAD_SINK,
-					    MEDIA_LNK_FL_ENABLED);
-		if (ret)
-			return ret;
-
-		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
-					    capture, 0,
-					    MEDIA_LNK_FL_ENABLED |
-					    MEDIA_LNK_FL_IMMUTABLE);
-		if (ret)
-			return ret;
-	}
-
-	/* params links */
-	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
-				    &rkisp1->isp.sd.entity,
-				    RKISP1_ISP_PAD_SINK_PARAMS,
-				    MEDIA_LNK_FL_ENABLED |
-				    MEDIA_LNK_FL_IMMUTABLE);
-	if (ret)
-		return ret;
-
-	/* 3A stats links */
-	return media_create_pad_link(&rkisp1->isp.sd.entity,
-				     RKISP1_ISP_PAD_SOURCE_STATS,
-				     &rkisp1->stats.vnode.vdev.entity, 0,
-				     MEDIA_LNK_FL_ENABLED |
-				     MEDIA_LNK_FL_IMMUTABLE);
-}
-
 static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 					struct v4l2_subdev *sd,
 					struct v4l2_async_subdev *asd)
@@ -210,19 +166,8 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
 {
 	struct rkisp1_device *rkisp1 =
 		container_of(notifier, struct rkisp1_device, notifier);
-	int ret;
-
-	ret = rkisp1_create_links(rkisp1);
-	if (ret)
-		return ret;
-
-	ret = v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
-	if (ret)
-		return ret;
-
-	dev_dbg(rkisp1->dev, "Async subdev notifier completed\n");
 
-	return 0;
+	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
 }
 
 static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
@@ -332,6 +277,50 @@ static const struct dev_pm_ops rkisp1_pm_ops = {
  * Core
  */
 
+static int rkisp1_create_links(struct rkisp1_device *rkisp1)
+{
+	unsigned int i;
+	int ret;
+
+	/* create ISP->RSZ->CAP links */
+	for (i = 0; i < 2; i++) {
+		struct media_entity *resizer =
+			&rkisp1->resizer_devs[i].sd.entity;
+		struct media_entity *capture =
+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
+
+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
+					    resizer, RKISP1_RSZ_PAD_SINK,
+					    MEDIA_LNK_FL_ENABLED);
+		if (ret)
+			return ret;
+
+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
+					    capture, 0,
+					    MEDIA_LNK_FL_ENABLED |
+					    MEDIA_LNK_FL_IMMUTABLE);
+		if (ret)
+			return ret;
+	}
+
+	/* params links */
+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_PARAMS,
+				    MEDIA_LNK_FL_ENABLED |
+				    MEDIA_LNK_FL_IMMUTABLE);
+	if (ret)
+		return ret;
+
+	/* 3A stats links */
+	return media_create_pad_link(&rkisp1->isp.sd.entity,
+				     RKISP1_ISP_PAD_SOURCE_STATS,
+				     &rkisp1->stats.vnode.vdev.entity, 0,
+				     MEDIA_LNK_FL_ENABLED |
+				     MEDIA_LNK_FL_IMMUTABLE);
+}
+
 static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
 {
 	rkisp1_params_unregister(rkisp1);
@@ -365,6 +354,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
+	ret = rkisp1_create_links(rkisp1);
+	if (ret)
+		goto error;
+
 	ret = rkisp1_subdev_notifier(rkisp1);
 	if (ret) {
 		dev_err(rkisp1->dev,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 14/55] media: rkisp1: Create internal links at probe time
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

There's no need to wait until all async subdevs are bound before
creating internal links. Create them at probe time.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 105 ++++++++----------
 1 file changed, 49 insertions(+), 56 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 4501aea265cb..7bb1235cddea 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -109,50 +109,6 @@ struct rkisp1_isr_data {
  * Sensor DT bindings
  */
 
-static int rkisp1_create_links(struct rkisp1_device *rkisp1)
-{
-	unsigned int i;
-	int ret;
-
-	/* create ISP->RSZ->CAP links */
-	for (i = 0; i < 2; i++) {
-		struct media_entity *resizer =
-			&rkisp1->resizer_devs[i].sd.entity;
-		struct media_entity *capture =
-			&rkisp1->capture_devs[i].vnode.vdev.entity;;
-
-		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
-					    RKISP1_ISP_PAD_SOURCE_VIDEO,
-					    resizer, RKISP1_RSZ_PAD_SINK,
-					    MEDIA_LNK_FL_ENABLED);
-		if (ret)
-			return ret;
-
-		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
-					    capture, 0,
-					    MEDIA_LNK_FL_ENABLED |
-					    MEDIA_LNK_FL_IMMUTABLE);
-		if (ret)
-			return ret;
-	}
-
-	/* params links */
-	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
-				    &rkisp1->isp.sd.entity,
-				    RKISP1_ISP_PAD_SINK_PARAMS,
-				    MEDIA_LNK_FL_ENABLED |
-				    MEDIA_LNK_FL_IMMUTABLE);
-	if (ret)
-		return ret;
-
-	/* 3A stats links */
-	return media_create_pad_link(&rkisp1->isp.sd.entity,
-				     RKISP1_ISP_PAD_SOURCE_STATS,
-				     &rkisp1->stats.vnode.vdev.entity, 0,
-				     MEDIA_LNK_FL_ENABLED |
-				     MEDIA_LNK_FL_IMMUTABLE);
-}
-
 static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 					struct v4l2_subdev *sd,
 					struct v4l2_async_subdev *asd)
@@ -210,19 +166,8 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
 {
 	struct rkisp1_device *rkisp1 =
 		container_of(notifier, struct rkisp1_device, notifier);
-	int ret;
-
-	ret = rkisp1_create_links(rkisp1);
-	if (ret)
-		return ret;
-
-	ret = v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
-	if (ret)
-		return ret;
-
-	dev_dbg(rkisp1->dev, "Async subdev notifier completed\n");
 
-	return 0;
+	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
 }
 
 static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
@@ -332,6 +277,50 @@ static const struct dev_pm_ops rkisp1_pm_ops = {
  * Core
  */
 
+static int rkisp1_create_links(struct rkisp1_device *rkisp1)
+{
+	unsigned int i;
+	int ret;
+
+	/* create ISP->RSZ->CAP links */
+	for (i = 0; i < 2; i++) {
+		struct media_entity *resizer =
+			&rkisp1->resizer_devs[i].sd.entity;
+		struct media_entity *capture =
+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
+
+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
+					    resizer, RKISP1_RSZ_PAD_SINK,
+					    MEDIA_LNK_FL_ENABLED);
+		if (ret)
+			return ret;
+
+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
+					    capture, 0,
+					    MEDIA_LNK_FL_ENABLED |
+					    MEDIA_LNK_FL_IMMUTABLE);
+		if (ret)
+			return ret;
+	}
+
+	/* params links */
+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_PARAMS,
+				    MEDIA_LNK_FL_ENABLED |
+				    MEDIA_LNK_FL_IMMUTABLE);
+	if (ret)
+		return ret;
+
+	/* 3A stats links */
+	return media_create_pad_link(&rkisp1->isp.sd.entity,
+				     RKISP1_ISP_PAD_SOURCE_STATS,
+				     &rkisp1->stats.vnode.vdev.entity, 0,
+				     MEDIA_LNK_FL_ENABLED |
+				     MEDIA_LNK_FL_IMMUTABLE);
+}
+
 static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
 {
 	rkisp1_params_unregister(rkisp1);
@@ -365,6 +354,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
+	ret = rkisp1_create_links(rkisp1);
+	if (ret)
+		goto error;
+
 	ret = rkisp1_subdev_notifier(rkisp1);
 	if (ret) {
 		dev_err(rkisp1->dev,
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 15/55] media: rkisp1: Rename rkisp1_subdev_notifier() to rkisp1_subdev_notifier_register()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The function name isn't very clear, rename it to
rkisp1_subdev_notifier_register().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 7bb1235cddea..386c1c17aec2 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -176,7 +176,7 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
 	.complete = rkisp1_subdev_notifier_complete,
 };
 
-static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
+static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
 	unsigned int next_id = 0;
@@ -358,7 +358,7 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
-	ret = rkisp1_subdev_notifier(rkisp1);
+	ret = rkisp1_subdev_notifier_register(rkisp1);
 	if (ret) {
 		dev_err(rkisp1->dev,
 			"Failed to register subdev notifier(%d)\n", ret);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 15/55] media: rkisp1: Rename rkisp1_subdev_notifier() to rkisp1_subdev_notifier_register()
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The function name isn't very clear, rename it to
rkisp1_subdev_notifier_register().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 7bb1235cddea..386c1c17aec2 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -176,7 +176,7 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
 	.complete = rkisp1_subdev_notifier_complete,
 };
 
-static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
+static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
 	unsigned int next_id = 0;
@@ -358,7 +358,7 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
-	ret = rkisp1_subdev_notifier(rkisp1);
+	ret = rkisp1_subdev_notifier_register(rkisp1);
 	if (ret) {
 		dev_err(rkisp1->dev,
 			"Failed to register subdev notifier(%d)\n", ret);
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Drivers typically extend the v4l2_async_subdev structure by embedding it
in a driver-specific structure, to store per-subdev custom data. The
v4l2_async_subdev instances are freed by the v4l2-async framework, which
makes this mechanism cumbersome to use safely when custom data needs
special treatment to be destroyed (such as freeing additional memory, or
releasing references to kernel objects).

To ease this, add a .destroy() operation to the
v4l2_async_notifier_operations structure. The operation is called right
before the v4l2_async_subdev is freed, giving drivers a chance to
destroy data if needed.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 Documentation/driver-api/media/v4l2-subdev.rst |  6 ++++++
 drivers/media/v4l2-core/v4l2-async.c           | 10 ++++++++++
 include/media/v4l2-async.h                     |  2 ++
 3 files changed, 18 insertions(+)

diff --git a/Documentation/driver-api/media/v4l2-subdev.rst b/Documentation/driver-api/media/v4l2-subdev.rst
index cf3b52bdbfb9..6f8d79926aa5 100644
--- a/Documentation/driver-api/media/v4l2-subdev.rst
+++ b/Documentation/driver-api/media/v4l2-subdev.rst
@@ -243,6 +243,12 @@ notifier callback is called. After all subdevices have been located the
 .complete() callback is called. When a subdevice is removed from the
 system the .unbind() method is called. All three callbacks are optional.
 
+Drivers can store any type of custom data in their driver-specific
+:c:type:`v4l2_async_subdev` wrapper. If any of that data requires special
+handling when the structure is freed, drivers must implement the ``.destroy()``
+notifier callback. The framework will call it right before freeing the
+:c:type:`v4l2_async_subdev`.
+
 Calling subdev operations
 ~~~~~~~~~~~~~~~~~~~~~~~~~
 
diff --git a/drivers/media/v4l2-core/v4l2-async.c b/drivers/media/v4l2-core/v4l2-async.c
index c6995718237a..735dede624b8 100644
--- a/drivers/media/v4l2-core/v4l2-async.c
+++ b/drivers/media/v4l2-core/v4l2-async.c
@@ -52,6 +52,15 @@ static int v4l2_async_nf_call_complete(struct v4l2_async_notifier *n)
 	return n->ops->complete(n);
 }
 
+static void v4l2_async_nf_call_destroy(struct v4l2_async_notifier *n,
+				       struct v4l2_async_subdev *asd)
+{
+	if (!n->ops || !n->ops->destroy)
+		return;
+
+	n->ops->destroy(asd);
+}
+
 static bool match_i2c(struct v4l2_async_notifier *notifier,
 		      struct v4l2_subdev *sd, struct v4l2_async_subdev *asd)
 {
@@ -626,6 +635,7 @@ static void __v4l2_async_nf_cleanup(struct v4l2_async_notifier *notifier)
 		}
 
 		list_del(&asd->asd_list);
+		v4l2_async_nf_call_destroy(notifier, asd);
 		kfree(asd);
 	}
 }
diff --git a/include/media/v4l2-async.h b/include/media/v4l2-async.h
index 13ff3ad948f4..25eb1d138c06 100644
--- a/include/media/v4l2-async.h
+++ b/include/media/v4l2-async.h
@@ -81,6 +81,7 @@ struct v4l2_async_subdev {
  * @complete:	All subdevices have been probed successfully. The complete
  *		callback is only executed for the root notifier.
  * @unbind:	a subdevice is leaving
+ * @destroy:	the asd is about to be freed
  */
 struct v4l2_async_notifier_operations {
 	int (*bound)(struct v4l2_async_notifier *notifier,
@@ -90,6 +91,7 @@ struct v4l2_async_notifier_operations {
 	void (*unbind)(struct v4l2_async_notifier *notifier,
 		       struct v4l2_subdev *subdev,
 		       struct v4l2_async_subdev *asd);
+	void (*destroy)(struct v4l2_async_subdev *asd);
 };
 
 /**
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Drivers typically extend the v4l2_async_subdev structure by embedding it
in a driver-specific structure, to store per-subdev custom data. The
v4l2_async_subdev instances are freed by the v4l2-async framework, which
makes this mechanism cumbersome to use safely when custom data needs
special treatment to be destroyed (such as freeing additional memory, or
releasing references to kernel objects).

To ease this, add a .destroy() operation to the
v4l2_async_notifier_operations structure. The operation is called right
before the v4l2_async_subdev is freed, giving drivers a chance to
destroy data if needed.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 Documentation/driver-api/media/v4l2-subdev.rst |  6 ++++++
 drivers/media/v4l2-core/v4l2-async.c           | 10 ++++++++++
 include/media/v4l2-async.h                     |  2 ++
 3 files changed, 18 insertions(+)

diff --git a/Documentation/driver-api/media/v4l2-subdev.rst b/Documentation/driver-api/media/v4l2-subdev.rst
index cf3b52bdbfb9..6f8d79926aa5 100644
--- a/Documentation/driver-api/media/v4l2-subdev.rst
+++ b/Documentation/driver-api/media/v4l2-subdev.rst
@@ -243,6 +243,12 @@ notifier callback is called. After all subdevices have been located the
 .complete() callback is called. When a subdevice is removed from the
 system the .unbind() method is called. All three callbacks are optional.
 
+Drivers can store any type of custom data in their driver-specific
+:c:type:`v4l2_async_subdev` wrapper. If any of that data requires special
+handling when the structure is freed, drivers must implement the ``.destroy()``
+notifier callback. The framework will call it right before freeing the
+:c:type:`v4l2_async_subdev`.
+
 Calling subdev operations
 ~~~~~~~~~~~~~~~~~~~~~~~~~
 
diff --git a/drivers/media/v4l2-core/v4l2-async.c b/drivers/media/v4l2-core/v4l2-async.c
index c6995718237a..735dede624b8 100644
--- a/drivers/media/v4l2-core/v4l2-async.c
+++ b/drivers/media/v4l2-core/v4l2-async.c
@@ -52,6 +52,15 @@ static int v4l2_async_nf_call_complete(struct v4l2_async_notifier *n)
 	return n->ops->complete(n);
 }
 
+static void v4l2_async_nf_call_destroy(struct v4l2_async_notifier *n,
+				       struct v4l2_async_subdev *asd)
+{
+	if (!n->ops || !n->ops->destroy)
+		return;
+
+	n->ops->destroy(asd);
+}
+
 static bool match_i2c(struct v4l2_async_notifier *notifier,
 		      struct v4l2_subdev *sd, struct v4l2_async_subdev *asd)
 {
@@ -626,6 +635,7 @@ static void __v4l2_async_nf_cleanup(struct v4l2_async_notifier *notifier)
 		}
 
 		list_del(&asd->asd_list);
+		v4l2_async_nf_call_destroy(notifier, asd);
 		kfree(asd);
 	}
 }
diff --git a/include/media/v4l2-async.h b/include/media/v4l2-async.h
index 13ff3ad948f4..25eb1d138c06 100644
--- a/include/media/v4l2-async.h
+++ b/include/media/v4l2-async.h
@@ -81,6 +81,7 @@ struct v4l2_async_subdev {
  * @complete:	All subdevices have been probed successfully. The complete
  *		callback is only executed for the root notifier.
  * @unbind:	a subdevice is leaving
+ * @destroy:	the asd is about to be freed
  */
 struct v4l2_async_notifier_operations {
 	int (*bound)(struct v4l2_async_notifier *notifier,
@@ -90,6 +91,7 @@ struct v4l2_async_notifier_operations {
 	void (*unbind)(struct v4l2_async_notifier *notifier,
 		       struct v4l2_subdev *subdev,
 		       struct v4l2_async_subdev *asd);
+	void (*destroy)(struct v4l2_async_subdev *asd);
 };
 
 /**
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

When a sensor is bound, its source pad is retrieved in the .bound()
operation with a call to media_entity_get_fwnode_pad(). The function
should be called with the source endpoint fwnode of the sensor, but is
instead called with the sensor's device fwnode.

Fix this, which involves storing a reference to the source endpoint
fwnode in the rkisp1_sensor_async structure, and thus implementing the
subdev notifier .destroy() operation to release the reference.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 28 ++++++++++++++++---
 2 files changed, 26 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index ba11baf75fa9..60c5462e1746 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -117,6 +117,7 @@ struct rkisp1_info {
  *
  * @asd:		async_subdev variable for the sensor
  * @index:		index of the sensor (counting sensor found in DT)
+ * @source_ep:		fwnode for the sensor source endpoint
  * @lanes:		number of lanes
  * @mbus_type:		type of bus (currently only CSI2 is supported)
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
@@ -127,6 +128,7 @@ struct rkisp1_info {
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
 	unsigned int index;
+	struct fwnode_handle *source_ep;
 	unsigned int lanes;
 	enum v4l2_mbus_type mbus_type;
 	unsigned int mbus_flags;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 386c1c17aec2..0f3e45cdbf2a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -138,7 +138,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 	phy_init(s_asd->dphy);
 
 	/* Create the link to the sensor. */
-	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
+	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
 						 MEDIA_PAD_FL_SOURCE);
 	if (source_pad < 0) {
 		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
@@ -170,10 +170,19 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
 	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
 }
 
+static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
+{
+	struct rkisp1_sensor_async *rk_asd =
+		container_of(asd, struct rkisp1_sensor_async, asd);
+
+	fwnode_handle_put(rk_asd->source_ep);
+}
+
 static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
 	.bound = rkisp1_subdev_notifier_bound,
 	.unbind = rkisp1_subdev_notifier_unbind,
 	.complete = rkisp1_subdev_notifier_complete,
+	.destroy = rkisp1_subdev_notifier_destroy,
 };
 
 static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
@@ -190,6 +199,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 			.bus_type = V4L2_MBUS_CSI2_DPHY
 		};
 		struct rkisp1_sensor_async *rk_asd;
+		struct fwnode_handle *source = NULL;
 		struct fwnode_handle *ep;
 
 		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
@@ -202,15 +212,24 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 		if (ret)
 			goto err_parse;
 
-		rk_asd = v4l2_async_nf_add_fwnode_remote(ntf, ep,
-							 struct
-							 rkisp1_sensor_async);
+		source = fwnode_graph_get_remote_endpoint(ep);
+		if (!source) {
+			dev_err(rkisp1->dev,
+				"endpoint %pfw has no remote endpoint\n",
+				ep);
+			ret = -ENODEV;
+			goto err_parse;
+		}
+
+		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
+						  struct rkisp1_sensor_async);
 		if (IS_ERR(rk_asd)) {
 			ret = PTR_ERR(rk_asd);
 			goto err_parse;
 		}
 
 		rk_asd->index = index++;
+		rk_asd->source_ep = source;
 		rk_asd->mbus_type = vep.bus_type;
 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
@@ -225,6 +244,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 		continue;
 err_parse:
 		fwnode_handle_put(ep);
+		fwnode_handle_put(source);
 		v4l2_async_nf_cleanup(ntf);
 		return ret;
 	}
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

When a sensor is bound, its source pad is retrieved in the .bound()
operation with a call to media_entity_get_fwnode_pad(). The function
should be called with the source endpoint fwnode of the sensor, but is
instead called with the sensor's device fwnode.

Fix this, which involves storing a reference to the source endpoint
fwnode in the rkisp1_sensor_async structure, and thus implementing the
subdev notifier .destroy() operation to release the reference.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 28 ++++++++++++++++---
 2 files changed, 26 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index ba11baf75fa9..60c5462e1746 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -117,6 +117,7 @@ struct rkisp1_info {
  *
  * @asd:		async_subdev variable for the sensor
  * @index:		index of the sensor (counting sensor found in DT)
+ * @source_ep:		fwnode for the sensor source endpoint
  * @lanes:		number of lanes
  * @mbus_type:		type of bus (currently only CSI2 is supported)
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
@@ -127,6 +128,7 @@ struct rkisp1_info {
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
 	unsigned int index;
+	struct fwnode_handle *source_ep;
 	unsigned int lanes;
 	enum v4l2_mbus_type mbus_type;
 	unsigned int mbus_flags;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 386c1c17aec2..0f3e45cdbf2a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -138,7 +138,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 	phy_init(s_asd->dphy);
 
 	/* Create the link to the sensor. */
-	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
+	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
 						 MEDIA_PAD_FL_SOURCE);
 	if (source_pad < 0) {
 		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
@@ -170,10 +170,19 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
 	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
 }
 
+static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
+{
+	struct rkisp1_sensor_async *rk_asd =
+		container_of(asd, struct rkisp1_sensor_async, asd);
+
+	fwnode_handle_put(rk_asd->source_ep);
+}
+
 static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
 	.bound = rkisp1_subdev_notifier_bound,
 	.unbind = rkisp1_subdev_notifier_unbind,
 	.complete = rkisp1_subdev_notifier_complete,
+	.destroy = rkisp1_subdev_notifier_destroy,
 };
 
 static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
@@ -190,6 +199,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 			.bus_type = V4L2_MBUS_CSI2_DPHY
 		};
 		struct rkisp1_sensor_async *rk_asd;
+		struct fwnode_handle *source = NULL;
 		struct fwnode_handle *ep;
 
 		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
@@ -202,15 +212,24 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 		if (ret)
 			goto err_parse;
 
-		rk_asd = v4l2_async_nf_add_fwnode_remote(ntf, ep,
-							 struct
-							 rkisp1_sensor_async);
+		source = fwnode_graph_get_remote_endpoint(ep);
+		if (!source) {
+			dev_err(rkisp1->dev,
+				"endpoint %pfw has no remote endpoint\n",
+				ep);
+			ret = -ENODEV;
+			goto err_parse;
+		}
+
+		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
+						  struct rkisp1_sensor_async);
 		if (IS_ERR(rk_asd)) {
 			ret = PTR_ERR(rk_asd);
 			goto err_parse;
 		}
 
 		rk_asd->index = index++;
+		rk_asd->source_ep = source;
 		rk_asd->mbus_type = vep.bus_type;
 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
@@ -225,6 +244,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 		continue;
 err_parse:
 		fwnode_handle_put(ep);
+		fwnode_handle_put(source);
 		v4l2_async_nf_cleanup(ntf);
 		return ret;
 	}
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 18/55] media: rkisp1: Split CSI handling to separate file
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Not all ISP instances include a MIPI CSI-2 receiver. To prepare for
making it optional, move code related to the CSI-2 receiver to a
separate file.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/Makefile   |   1 +
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 +-
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 193 ++++++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +++
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  32 +--
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 153 +-------------
 6 files changed, 257 insertions(+), 167 deletions(-)
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h

diff --git a/drivers/media/platform/rockchip/rkisp1/Makefile b/drivers/media/platform/rockchip/rkisp1/Makefile
index f7543a82aa10..b3844c4f7623 100644
--- a/drivers/media/platform/rockchip/rkisp1/Makefile
+++ b/drivers/media/platform/rockchip/rkisp1/Makefile
@@ -2,6 +2,7 @@
 
 rockchip-isp1-y := rkisp1-capture.o \
 		   rkisp1-common.o \
+		   rkisp1-csi.o \
 		   rkisp1-dev.o \
 		   rkisp1-isp.o \
 		   rkisp1-resizer.o \
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 60c5462e1746..a52fa9e0dd66 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -123,7 +123,6 @@ struct rkisp1_info {
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
  * @sd:			a pointer to v4l2_subdev struct of the sensor
  * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
- * @dphy:		a pointer to the phy
  */
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
@@ -134,7 +133,19 @@ struct rkisp1_sensor_async {
 	unsigned int mbus_flags;
 	struct v4l2_subdev *sd;
 	struct v4l2_ctrl *pixel_rate_ctrl;
+};
+
+/*
+ * struct rkisp1_csi - CSI receiver subdev
+ *
+ * @rkisp1: pointer to the rkisp1 device
+ * @dphy: a pointer to the phy
+ * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
+ */
+struct rkisp1_csi {
+	struct rkisp1_device *rkisp1;
 	struct phy *dphy;
+	bool is_dphy_errctrl_disabled;
 };
 
 /*
@@ -147,7 +158,6 @@ struct rkisp1_sensor_async {
  * @sink_fmt:			input format
  * @src_fmt:			output format
  * @ops_lock:			ops serialization
- * @is_dphy_errctrl_disabled:	if dphy errctrl is disabled (avoid endless interrupt)
  * @frame_sequence:		used to synchronize frame_id between video devices.
  */
 struct rkisp1_isp {
@@ -157,7 +167,6 @@ struct rkisp1_isp {
 	const struct rkisp1_mbus_info *sink_fmt;
 	const struct rkisp1_mbus_info *src_fmt;
 	struct mutex ops_lock; /* serialize the subdevice ops */
-	bool is_dphy_errctrl_disabled;
 	__u32 frame_sequence;
 };
 
@@ -411,6 +420,7 @@ struct rkisp1_debug {
  * @media_dev:	   media_device variable
  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
  * @active_sensor: sensor in-use, set when streaming on
+ * @csi:	   internal CSI-2 receiver
  * @isp:	   ISP sub-device
  * @resizer_devs:  resizer sub-devices
  * @capture_devs:  capture devices
@@ -430,6 +440,7 @@ struct rkisp1_device {
 	struct media_device media_dev;
 	struct v4l2_async_notifier notifier;
 	struct rkisp1_sensor_async *active_sensor;
+	struct rkisp1_csi csi;
 	struct rkisp1_isp isp;
 	struct rkisp1_resizer resizer_devs[2];
 	struct rkisp1_capture capture_devs[2];
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
new file mode 100644
index 000000000000..4af04296b625
--- /dev/null
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -0,0 +1,193 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+/*
+ * Rockchip ISP1 Driver - CSI-2 Receiver
+ *
+ * Copyright (C) 2019 Collabora, Ltd.
+ * Copyright (C) 2022 Ideas on Board
+ *
+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
+ */
+
+#include <linux/device.h>
+#include <linux/phy/phy.h>
+#include <linux/phy/phy-mipi-dphy.h>
+
+#include <media/v4l2-ctrls.h>
+
+#include "rkisp1-common.h"
+#include "rkisp1-csi.h"
+
+int rkisp1_config_mipi(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	unsigned int lanes = rkisp1->active_sensor->lanes;
+	u32 mipi_ctrl;
+
+	if (lanes < 1 || lanes > 4)
+		return -EINVAL;
+
+	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
+		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
+		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
+		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
+
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
+
+	/* V12 could also use a newer csi2-host, but we don't want that yet */
+	if (rkisp1->info->isp_ver == RKISP1_V12)
+		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
+
+	/* Configure Data Type and Virtual Channel */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
+		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
+		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
+
+	/* Clear MIPI interrupts */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
+	/*
+	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
+	 * isp bus may be dead when switch isp.
+	 */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
+		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
+		     RKISP1_CIF_MIPI_ERR_DPHY |
+		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
+		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
+
+	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
+		"  MIPI_IMG_DATA_SEL 0x%08x\n"
+		"  MIPI_STATUS 0x%08x\n"
+		"  MIPI_IMSC 0x%08x\n",
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
+
+	return 0;
+}
+
+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
+			   struct rkisp1_sensor_async *sensor)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	union phy_configure_opts opts;
+	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
+	s64 pixel_clock;
+
+	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
+	if (!pixel_clock) {
+		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
+		return -EINVAL;
+	}
+
+	phy_mipi_dphy_get_default_config(pixel_clock,
+					 rkisp1->isp.sink_fmt->bus_width,
+					 sensor->lanes, cfg);
+	phy_set_mode(csi->dphy, PHY_MODE_MIPI_DPHY);
+	phy_configure(csi->dphy, &opts);
+	phy_power_on(csi->dphy);
+
+	return 0;
+}
+
+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
+{
+	phy_power_off(csi->dphy);
+}
+
+void rkisp1_mipi_start(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
+}
+
+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	/* Mask and clear interrupts. */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+}
+
+irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
+{
+	struct device *dev = ctx;
+	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
+	u32 val, status;
+
+	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
+	if (!status)
+		return IRQ_NONE;
+
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
+
+	/*
+	 * Disable DPHY errctrl interrupt, because this dphy
+	 * erctrl signal is asserted until the next changes
+	 * of line state. This time is may be too long and cpu
+	 * is hold in this interrupt.
+	 */
+	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
+		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
+		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
+			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
+		rkisp1->csi.is_dphy_errctrl_disabled = true;
+	}
+
+	/*
+	 * Enable DPHY errctrl interrupt again, if mipi have receive
+	 * the whole frame without any error.
+	 */
+	if (status == RKISP1_CIF_MIPI_FRAME_END) {
+		/*
+		 * Enable DPHY errctrl interrupt again, if mipi have receive
+		 * the whole frame without any error.
+		 */
+		if (rkisp1->csi.is_dphy_errctrl_disabled) {
+			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
+			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
+			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
+			rkisp1->csi.is_dphy_errctrl_disabled = false;
+		}
+	} else {
+		rkisp1->debug.mipi_error++;
+	}
+
+	return IRQ_HANDLED;
+}
+
+int rkisp1_csi_init(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+
+	csi->dphy = devm_phy_get(rkisp1->dev, "dphy");
+	if (IS_ERR(csi->dphy)) {
+		if (PTR_ERR(csi->dphy) != -EPROBE_DEFER)
+		dev_err_probe(rkisp1->dev, PTR_ERR(csi->dphy),
+			      "Couldn't get the MIPI D-PHY\n");
+		return PTR_ERR(csi->dphy);
+	}
+
+	phy_init(csi->dphy);
+
+	return 0;
+}
+
+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+
+	phy_exit(csi->dphy);
+}
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
new file mode 100644
index 000000000000..d97a4ee5c002
--- /dev/null
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -0,0 +1,28 @@
+/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
+/*
+ * Rockchip ISP1 Driver - CSI-2 Receiver
+ *
+ * Copyright (C) 2019 Collabora, Ltd.
+ * Copyright (C) 2022 Ideas on Board
+ *
+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
+ */
+#ifndef _RKISP1_CSI_H
+#define _RKISP1_CSI_H
+
+struct rkisp1_device;
+struct rkisp1_sensor_async;
+
+int rkisp1_csi_init(struct rkisp1_device *rkisp1);
+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
+
+int rkisp1_config_mipi(struct rkisp1_csi *csi);
+
+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
+			   struct rkisp1_sensor_async *sensor);
+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
+void rkisp1_mipi_start(struct rkisp1_csi *csi);
+void rkisp1_mipi_stop(struct rkisp1_csi *csi);
+
+#endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 0f3e45cdbf2a..373a1f00c10a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -15,11 +15,11 @@
 #include <linux/of_graph.h>
 #include <linux/of_platform.h>
 #include <linux/pinctrl/consumer.h>
-#include <linux/phy/phy.h>
-#include <linux/phy/phy-mipi-dphy.h>
+#include <linux/pm_runtime.h>
 #include <media/v4l2-fwnode.h>
 
 #include "rkisp1-common.h"
+#include "rkisp1-csi.h"
 
 /*
  * ISP Details
@@ -128,14 +128,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 	}
 
 	s_asd->sd = sd;
-	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
-	if (IS_ERR(s_asd->dphy)) {
-		if (PTR_ERR(s_asd->dphy) != -EPROBE_DEFER)
-			dev_err(rkisp1->dev, "Couldn't get the MIPI D-PHY\n");
-		return PTR_ERR(s_asd->dphy);
-	}
-
-	phy_init(s_asd->dphy);
 
 	/* Create the link to the sensor. */
 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
@@ -152,16 +144,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
 }
 
-static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
-					  struct v4l2_subdev *sd,
-					  struct v4l2_async_subdev *asd)
-{
-	struct rkisp1_sensor_async *s_asd =
-		container_of(asd, struct rkisp1_sensor_async, asd);
-
-	phy_exit(s_asd->dphy);
-}
-
 static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
 {
 	struct rkisp1_device *rkisp1 =
@@ -180,7 +162,6 @@ static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
 
 static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
 	.bound = rkisp1_subdev_notifier_bound,
-	.unbind = rkisp1_subdev_notifier_unbind,
 	.complete = rkisp1_subdev_notifier_complete,
 	.destroy = rkisp1_subdev_notifier_destroy,
 };
@@ -540,14 +521,20 @@ static int rkisp1_probe(struct platform_device *pdev)
 		goto err_unreg_v4l2_dev;
 	}
 
-	ret = rkisp1_entities_register(rkisp1);
+	ret = rkisp1_csi_init(rkisp1);
 	if (ret)
 		goto err_unreg_media_dev;
 
+	ret = rkisp1_entities_register(rkisp1);
+	if (ret)
+		goto err_cleanup_csi;
+
 	rkisp1_debug_init(rkisp1);
 
 	return 0;
 
+err_cleanup_csi:
+	rkisp1_csi_cleanup(rkisp1);
 err_unreg_media_dev:
 	media_device_unregister(&rkisp1->media_dev);
 err_unreg_v4l2_dev:
@@ -565,6 +552,7 @@ static int rkisp1_remove(struct platform_device *pdev)
 	v4l2_async_nf_cleanup(&rkisp1->notifier);
 
 	rkisp1_entities_unregister(rkisp1);
+	rkisp1_csi_cleanup(rkisp1);
 	rkisp1_debug_cleanup(rkisp1);
 
 	media_device_unregister(&rkisp1->media_dev);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 81138c676ac0..5eabb321e320 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -9,8 +9,6 @@
  */
 
 #include <linux/iopoll.h>
-#include <linux/phy/phy.h>
-#include <linux/phy/phy-mipi-dphy.h>
 #include <linux/pm_runtime.h>
 #include <linux/videodev2.h>
 #include <linux/vmalloc.h>
@@ -18,6 +16,7 @@
 #include <media/v4l2-event.h>
 
 #include "rkisp1-common.h"
+#include "rkisp1-csi.h"
 
 #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
 #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
@@ -265,55 +264,6 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 	return 0;
 }
 
-static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
-{
-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
-	unsigned int lanes = rkisp1->active_sensor->lanes;
-	u32 mipi_ctrl;
-
-	if (lanes < 1 || lanes > 4)
-		return -EINVAL;
-
-	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
-		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
-		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
-		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
-
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
-
-	/* V12 could also use a newer csi2-host, but we don't want that yet */
-	if (rkisp1->info->isp_ver == RKISP1_V12)
-		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
-
-	/* Configure Data Type and Virtual Channel */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
-		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
-		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
-
-	/* Clear MIPI interrupts */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
-	/*
-	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
-	 * isp bus may be dead when switch isp.
-	 */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
-		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
-		     RKISP1_CIF_MIPI_ERR_DPHY |
-		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
-		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
-
-	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
-		"  MIPI_IMG_DATA_SEL 0x%08x\n"
-		"  MIPI_STATUS 0x%08x\n"
-		"  MIPI_IMSC 0x%08x\n",
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
-
-	return 0;
-}
-
 /* Configure MUX */
 static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 {
@@ -326,7 +276,7 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 		ret = rkisp1_config_dvp(rkisp1);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
-		ret = rkisp1_config_mipi(rkisp1);
+		ret = rkisp1_config_mipi(&rkisp1->csi);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
@@ -360,17 +310,14 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
 	 * Stop ISP(isp) ->wait for ISP isp off
 	 */
 	/* stop and clear MI, MIPI, and ISP interrupts */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
-
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
 
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+
+	rkisp1_mipi_stop(&rkisp1->csi);
+
 	/* stop ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
@@ -417,11 +364,9 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
 	rkisp1_config_clk(rkisp1);
 
 	/* Activate MIPI */
-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-			     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
-	}
+	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
+		rkisp1_mipi_start(&rkisp1->csi);
+
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
@@ -814,35 +759,6 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
  * Stream operations
  */
 
-static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
-				  struct rkisp1_sensor_async *sensor)
-{
-	struct rkisp1_device *rkisp1 =
-		container_of(isp->sd.v4l2_dev, struct rkisp1_device, v4l2_dev);
-	union phy_configure_opts opts;
-	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
-	s64 pixel_clock;
-
-	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
-	if (!pixel_clock) {
-		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
-		return -EINVAL;
-	}
-
-	phy_mipi_dphy_get_default_config(pixel_clock, isp->sink_fmt->bus_width,
-					 sensor->lanes, cfg);
-	phy_set_mode(sensor->dphy, PHY_MODE_MIPI_DPHY);
-	phy_configure(sensor->dphy, &opts);
-	phy_power_on(sensor->dphy);
-
-	return 0;
-}
-
-static void rkisp1_mipi_csi2_stop(struct rkisp1_sensor_async *sensor)
-{
-	phy_power_off(sensor->dphy);
-}
-
 static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_device *rkisp1 =
@@ -856,7 +772,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 				 false);
 
 		rkisp1_isp_stop(rkisp1);
-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
 		return 0;
 	}
 
@@ -878,7 +794,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (ret)
 		goto mutex_unlock;
 
-	ret = rkisp1_mipi_csi2_start(&rkisp1->isp, rkisp1->active_sensor);
+	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
 	if (ret)
 		goto mutex_unlock;
 
@@ -888,7 +804,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 			       true);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
 
@@ -993,53 +909,6 @@ void rkisp1_isp_unregister(struct rkisp1_device *rkisp1)
  * Interrupt handlers
  */
 
-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
-{
-	struct device *dev = ctx;
-	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
-	u32 val, status;
-
-	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
-	if (!status)
-		return IRQ_NONE;
-
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
-
-	/*
-	 * Disable DPHY errctrl interrupt, because this dphy
-	 * erctrl signal is asserted until the next changes
-	 * of line state. This time is may be too long and cpu
-	 * is hold in this interrupt.
-	 */
-	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
-			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
-		rkisp1->isp.is_dphy_errctrl_disabled = true;
-	}
-
-	/*
-	 * Enable DPHY errctrl interrupt again, if mipi have receive
-	 * the whole frame without any error.
-	 */
-	if (status == RKISP1_CIF_MIPI_FRAME_END) {
-		/*
-		 * Enable DPHY errctrl interrupt again, if mipi have receive
-		 * the whole frame without any error.
-		 */
-		if (rkisp1->isp.is_dphy_errctrl_disabled) {
-			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
-			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
-			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
-			rkisp1->isp.is_dphy_errctrl_disabled = false;
-		}
-	} else {
-		rkisp1->debug.mipi_error++;
-	}
-
-	return IRQ_HANDLED;
-}
-
 static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
 {
 	struct v4l2_event event = {
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 18/55] media: rkisp1: Split CSI handling to separate file
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Not all ISP instances include a MIPI CSI-2 receiver. To prepare for
making it optional, move code related to the CSI-2 receiver to a
separate file.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/Makefile   |   1 +
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 +-
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 193 ++++++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +++
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  32 +--
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 153 +-------------
 6 files changed, 257 insertions(+), 167 deletions(-)
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
 create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h

diff --git a/drivers/media/platform/rockchip/rkisp1/Makefile b/drivers/media/platform/rockchip/rkisp1/Makefile
index f7543a82aa10..b3844c4f7623 100644
--- a/drivers/media/platform/rockchip/rkisp1/Makefile
+++ b/drivers/media/platform/rockchip/rkisp1/Makefile
@@ -2,6 +2,7 @@
 
 rockchip-isp1-y := rkisp1-capture.o \
 		   rkisp1-common.o \
+		   rkisp1-csi.o \
 		   rkisp1-dev.o \
 		   rkisp1-isp.o \
 		   rkisp1-resizer.o \
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 60c5462e1746..a52fa9e0dd66 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -123,7 +123,6 @@ struct rkisp1_info {
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
  * @sd:			a pointer to v4l2_subdev struct of the sensor
  * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
- * @dphy:		a pointer to the phy
  */
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
@@ -134,7 +133,19 @@ struct rkisp1_sensor_async {
 	unsigned int mbus_flags;
 	struct v4l2_subdev *sd;
 	struct v4l2_ctrl *pixel_rate_ctrl;
+};
+
+/*
+ * struct rkisp1_csi - CSI receiver subdev
+ *
+ * @rkisp1: pointer to the rkisp1 device
+ * @dphy: a pointer to the phy
+ * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
+ */
+struct rkisp1_csi {
+	struct rkisp1_device *rkisp1;
 	struct phy *dphy;
+	bool is_dphy_errctrl_disabled;
 };
 
 /*
@@ -147,7 +158,6 @@ struct rkisp1_sensor_async {
  * @sink_fmt:			input format
  * @src_fmt:			output format
  * @ops_lock:			ops serialization
- * @is_dphy_errctrl_disabled:	if dphy errctrl is disabled (avoid endless interrupt)
  * @frame_sequence:		used to synchronize frame_id between video devices.
  */
 struct rkisp1_isp {
@@ -157,7 +167,6 @@ struct rkisp1_isp {
 	const struct rkisp1_mbus_info *sink_fmt;
 	const struct rkisp1_mbus_info *src_fmt;
 	struct mutex ops_lock; /* serialize the subdevice ops */
-	bool is_dphy_errctrl_disabled;
 	__u32 frame_sequence;
 };
 
@@ -411,6 +420,7 @@ struct rkisp1_debug {
  * @media_dev:	   media_device variable
  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
  * @active_sensor: sensor in-use, set when streaming on
+ * @csi:	   internal CSI-2 receiver
  * @isp:	   ISP sub-device
  * @resizer_devs:  resizer sub-devices
  * @capture_devs:  capture devices
@@ -430,6 +440,7 @@ struct rkisp1_device {
 	struct media_device media_dev;
 	struct v4l2_async_notifier notifier;
 	struct rkisp1_sensor_async *active_sensor;
+	struct rkisp1_csi csi;
 	struct rkisp1_isp isp;
 	struct rkisp1_resizer resizer_devs[2];
 	struct rkisp1_capture capture_devs[2];
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
new file mode 100644
index 000000000000..4af04296b625
--- /dev/null
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -0,0 +1,193 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+/*
+ * Rockchip ISP1 Driver - CSI-2 Receiver
+ *
+ * Copyright (C) 2019 Collabora, Ltd.
+ * Copyright (C) 2022 Ideas on Board
+ *
+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
+ */
+
+#include <linux/device.h>
+#include <linux/phy/phy.h>
+#include <linux/phy/phy-mipi-dphy.h>
+
+#include <media/v4l2-ctrls.h>
+
+#include "rkisp1-common.h"
+#include "rkisp1-csi.h"
+
+int rkisp1_config_mipi(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	unsigned int lanes = rkisp1->active_sensor->lanes;
+	u32 mipi_ctrl;
+
+	if (lanes < 1 || lanes > 4)
+		return -EINVAL;
+
+	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
+		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
+		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
+		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
+
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
+
+	/* V12 could also use a newer csi2-host, but we don't want that yet */
+	if (rkisp1->info->isp_ver == RKISP1_V12)
+		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
+
+	/* Configure Data Type and Virtual Channel */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
+		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
+		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
+
+	/* Clear MIPI interrupts */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
+	/*
+	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
+	 * isp bus may be dead when switch isp.
+	 */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
+		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
+		     RKISP1_CIF_MIPI_ERR_DPHY |
+		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
+		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
+
+	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
+		"  MIPI_IMG_DATA_SEL 0x%08x\n"
+		"  MIPI_STATUS 0x%08x\n"
+		"  MIPI_IMSC 0x%08x\n",
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
+
+	return 0;
+}
+
+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
+			   struct rkisp1_sensor_async *sensor)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	union phy_configure_opts opts;
+	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
+	s64 pixel_clock;
+
+	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
+	if (!pixel_clock) {
+		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
+		return -EINVAL;
+	}
+
+	phy_mipi_dphy_get_default_config(pixel_clock,
+					 rkisp1->isp.sink_fmt->bus_width,
+					 sensor->lanes, cfg);
+	phy_set_mode(csi->dphy, PHY_MODE_MIPI_DPHY);
+	phy_configure(csi->dphy, &opts);
+	phy_power_on(csi->dphy);
+
+	return 0;
+}
+
+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
+{
+	phy_power_off(csi->dphy);
+}
+
+void rkisp1_mipi_start(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
+}
+
+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	/* Mask and clear interrupts. */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+}
+
+irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
+{
+	struct device *dev = ctx;
+	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
+	u32 val, status;
+
+	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
+	if (!status)
+		return IRQ_NONE;
+
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
+
+	/*
+	 * Disable DPHY errctrl interrupt, because this dphy
+	 * erctrl signal is asserted until the next changes
+	 * of line state. This time is may be too long and cpu
+	 * is hold in this interrupt.
+	 */
+	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
+		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
+		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
+			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
+		rkisp1->csi.is_dphy_errctrl_disabled = true;
+	}
+
+	/*
+	 * Enable DPHY errctrl interrupt again, if mipi have receive
+	 * the whole frame without any error.
+	 */
+	if (status == RKISP1_CIF_MIPI_FRAME_END) {
+		/*
+		 * Enable DPHY errctrl interrupt again, if mipi have receive
+		 * the whole frame without any error.
+		 */
+		if (rkisp1->csi.is_dphy_errctrl_disabled) {
+			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
+			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
+			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
+			rkisp1->csi.is_dphy_errctrl_disabled = false;
+		}
+	} else {
+		rkisp1->debug.mipi_error++;
+	}
+
+	return IRQ_HANDLED;
+}
+
+int rkisp1_csi_init(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+
+	csi->dphy = devm_phy_get(rkisp1->dev, "dphy");
+	if (IS_ERR(csi->dphy)) {
+		if (PTR_ERR(csi->dphy) != -EPROBE_DEFER)
+		dev_err_probe(rkisp1->dev, PTR_ERR(csi->dphy),
+			      "Couldn't get the MIPI D-PHY\n");
+		return PTR_ERR(csi->dphy);
+	}
+
+	phy_init(csi->dphy);
+
+	return 0;
+}
+
+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+
+	phy_exit(csi->dphy);
+}
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
new file mode 100644
index 000000000000..d97a4ee5c002
--- /dev/null
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -0,0 +1,28 @@
+/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
+/*
+ * Rockchip ISP1 Driver - CSI-2 Receiver
+ *
+ * Copyright (C) 2019 Collabora, Ltd.
+ * Copyright (C) 2022 Ideas on Board
+ *
+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
+ */
+#ifndef _RKISP1_CSI_H
+#define _RKISP1_CSI_H
+
+struct rkisp1_device;
+struct rkisp1_sensor_async;
+
+int rkisp1_csi_init(struct rkisp1_device *rkisp1);
+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
+
+int rkisp1_config_mipi(struct rkisp1_csi *csi);
+
+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
+			   struct rkisp1_sensor_async *sensor);
+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
+void rkisp1_mipi_start(struct rkisp1_csi *csi);
+void rkisp1_mipi_stop(struct rkisp1_csi *csi);
+
+#endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 0f3e45cdbf2a..373a1f00c10a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -15,11 +15,11 @@
 #include <linux/of_graph.h>
 #include <linux/of_platform.h>
 #include <linux/pinctrl/consumer.h>
-#include <linux/phy/phy.h>
-#include <linux/phy/phy-mipi-dphy.h>
+#include <linux/pm_runtime.h>
 #include <media/v4l2-fwnode.h>
 
 #include "rkisp1-common.h"
+#include "rkisp1-csi.h"
 
 /*
  * ISP Details
@@ -128,14 +128,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 	}
 
 	s_asd->sd = sd;
-	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
-	if (IS_ERR(s_asd->dphy)) {
-		if (PTR_ERR(s_asd->dphy) != -EPROBE_DEFER)
-			dev_err(rkisp1->dev, "Couldn't get the MIPI D-PHY\n");
-		return PTR_ERR(s_asd->dphy);
-	}
-
-	phy_init(s_asd->dphy);
 
 	/* Create the link to the sensor. */
 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
@@ -152,16 +144,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
 }
 
-static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
-					  struct v4l2_subdev *sd,
-					  struct v4l2_async_subdev *asd)
-{
-	struct rkisp1_sensor_async *s_asd =
-		container_of(asd, struct rkisp1_sensor_async, asd);
-
-	phy_exit(s_asd->dphy);
-}
-
 static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
 {
 	struct rkisp1_device *rkisp1 =
@@ -180,7 +162,6 @@ static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
 
 static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
 	.bound = rkisp1_subdev_notifier_bound,
-	.unbind = rkisp1_subdev_notifier_unbind,
 	.complete = rkisp1_subdev_notifier_complete,
 	.destroy = rkisp1_subdev_notifier_destroy,
 };
@@ -540,14 +521,20 @@ static int rkisp1_probe(struct platform_device *pdev)
 		goto err_unreg_v4l2_dev;
 	}
 
-	ret = rkisp1_entities_register(rkisp1);
+	ret = rkisp1_csi_init(rkisp1);
 	if (ret)
 		goto err_unreg_media_dev;
 
+	ret = rkisp1_entities_register(rkisp1);
+	if (ret)
+		goto err_cleanup_csi;
+
 	rkisp1_debug_init(rkisp1);
 
 	return 0;
 
+err_cleanup_csi:
+	rkisp1_csi_cleanup(rkisp1);
 err_unreg_media_dev:
 	media_device_unregister(&rkisp1->media_dev);
 err_unreg_v4l2_dev:
@@ -565,6 +552,7 @@ static int rkisp1_remove(struct platform_device *pdev)
 	v4l2_async_nf_cleanup(&rkisp1->notifier);
 
 	rkisp1_entities_unregister(rkisp1);
+	rkisp1_csi_cleanup(rkisp1);
 	rkisp1_debug_cleanup(rkisp1);
 
 	media_device_unregister(&rkisp1->media_dev);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 81138c676ac0..5eabb321e320 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -9,8 +9,6 @@
  */
 
 #include <linux/iopoll.h>
-#include <linux/phy/phy.h>
-#include <linux/phy/phy-mipi-dphy.h>
 #include <linux/pm_runtime.h>
 #include <linux/videodev2.h>
 #include <linux/vmalloc.h>
@@ -18,6 +16,7 @@
 #include <media/v4l2-event.h>
 
 #include "rkisp1-common.h"
+#include "rkisp1-csi.h"
 
 #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
 #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
@@ -265,55 +264,6 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 	return 0;
 }
 
-static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
-{
-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
-	unsigned int lanes = rkisp1->active_sensor->lanes;
-	u32 mipi_ctrl;
-
-	if (lanes < 1 || lanes > 4)
-		return -EINVAL;
-
-	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
-		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
-		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
-		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
-
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
-
-	/* V12 could also use a newer csi2-host, but we don't want that yet */
-	if (rkisp1->info->isp_ver == RKISP1_V12)
-		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
-
-	/* Configure Data Type and Virtual Channel */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
-		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
-		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
-
-	/* Clear MIPI interrupts */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
-	/*
-	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
-	 * isp bus may be dead when switch isp.
-	 */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
-		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
-		     RKISP1_CIF_MIPI_ERR_DPHY |
-		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
-		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
-
-	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
-		"  MIPI_IMG_DATA_SEL 0x%08x\n"
-		"  MIPI_STATUS 0x%08x\n"
-		"  MIPI_IMSC 0x%08x\n",
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
-
-	return 0;
-}
-
 /* Configure MUX */
 static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 {
@@ -326,7 +276,7 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 		ret = rkisp1_config_dvp(rkisp1);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
-		ret = rkisp1_config_mipi(rkisp1);
+		ret = rkisp1_config_mipi(&rkisp1->csi);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
@@ -360,17 +310,14 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
 	 * Stop ISP(isp) ->wait for ISP isp off
 	 */
 	/* stop and clear MI, MIPI, and ISP interrupts */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
-
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
 
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+
+	rkisp1_mipi_stop(&rkisp1->csi);
+
 	/* stop ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
@@ -417,11 +364,9 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
 	rkisp1_config_clk(rkisp1);
 
 	/* Activate MIPI */
-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-			     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
-	}
+	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
+		rkisp1_mipi_start(&rkisp1->csi);
+
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
@@ -814,35 +759,6 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
  * Stream operations
  */
 
-static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
-				  struct rkisp1_sensor_async *sensor)
-{
-	struct rkisp1_device *rkisp1 =
-		container_of(isp->sd.v4l2_dev, struct rkisp1_device, v4l2_dev);
-	union phy_configure_opts opts;
-	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
-	s64 pixel_clock;
-
-	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
-	if (!pixel_clock) {
-		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
-		return -EINVAL;
-	}
-
-	phy_mipi_dphy_get_default_config(pixel_clock, isp->sink_fmt->bus_width,
-					 sensor->lanes, cfg);
-	phy_set_mode(sensor->dphy, PHY_MODE_MIPI_DPHY);
-	phy_configure(sensor->dphy, &opts);
-	phy_power_on(sensor->dphy);
-
-	return 0;
-}
-
-static void rkisp1_mipi_csi2_stop(struct rkisp1_sensor_async *sensor)
-{
-	phy_power_off(sensor->dphy);
-}
-
 static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_device *rkisp1 =
@@ -856,7 +772,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 				 false);
 
 		rkisp1_isp_stop(rkisp1);
-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
 		return 0;
 	}
 
@@ -878,7 +794,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (ret)
 		goto mutex_unlock;
 
-	ret = rkisp1_mipi_csi2_start(&rkisp1->isp, rkisp1->active_sensor);
+	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
 	if (ret)
 		goto mutex_unlock;
 
@@ -888,7 +804,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 			       true);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
 
@@ -993,53 +909,6 @@ void rkisp1_isp_unregister(struct rkisp1_device *rkisp1)
  * Interrupt handlers
  */
 
-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
-{
-	struct device *dev = ctx;
-	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
-	u32 val, status;
-
-	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
-	if (!status)
-		return IRQ_NONE;
-
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
-
-	/*
-	 * Disable DPHY errctrl interrupt, because this dphy
-	 * erctrl signal is asserted until the next changes
-	 * of line state. This time is may be too long and cpu
-	 * is hold in this interrupt.
-	 */
-	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
-			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
-		rkisp1->isp.is_dphy_errctrl_disabled = true;
-	}
-
-	/*
-	 * Enable DPHY errctrl interrupt again, if mipi have receive
-	 * the whole frame without any error.
-	 */
-	if (status == RKISP1_CIF_MIPI_FRAME_END) {
-		/*
-		 * Enable DPHY errctrl interrupt again, if mipi have receive
-		 * the whole frame without any error.
-		 */
-		if (rkisp1->isp.is_dphy_errctrl_disabled) {
-			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
-			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
-			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
-			rkisp1->isp.is_dphy_errctrl_disabled = false;
-		}
-	} else {
-		rkisp1->debug.mipi_error++;
-	}
-
-	return IRQ_HANDLED;
-}
-
 static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
 {
 	struct v4l2_event event = {
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 19/55] media: rkisp1: isp: Start CSI-2 receiver before ISP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Make sure the ISP is ready to receive data before starting the CSI-2
receiver by starting it first. Similarly, stop the CSI-2 receiver before
the ISP when stopping streaming.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 11 +++++++----
 1 file changed, 7 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 5eabb321e320..0e68c8d53404 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -771,8 +771,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
 				 false);
 
-		rkisp1_isp_stop(rkisp1);
 		rkisp1_mipi_csi2_stop(&rkisp1->csi);
+		rkisp1_isp_stop(rkisp1);
+
 		return 0;
 	}
 
@@ -794,11 +795,13 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (ret)
 		goto mutex_unlock;
 
+	rkisp1_isp_start(rkisp1);
+
 	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
-	if (ret)
+	if (ret) {
+		rkisp1_isp_stop(rkisp1);
 		goto mutex_unlock;
-
-	rkisp1_isp_start(rkisp1);
+	}
 
 	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
 			       true);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 19/55] media: rkisp1: isp: Start CSI-2 receiver before ISP
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Make sure the ISP is ready to receive data before starting the CSI-2
receiver by starting it first. Similarly, stop the CSI-2 receiver before
the ISP when stopping streaming.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 11 +++++++----
 1 file changed, 7 insertions(+), 4 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 5eabb321e320..0e68c8d53404 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -771,8 +771,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
 				 false);
 
-		rkisp1_isp_stop(rkisp1);
 		rkisp1_mipi_csi2_stop(&rkisp1->csi);
+		rkisp1_isp_stop(rkisp1);
+
 		return 0;
 	}
 
@@ -794,11 +795,13 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (ret)
 		goto mutex_unlock;
 
+	rkisp1_isp_start(rkisp1);
+
 	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
-	if (ret)
+	if (ret) {
+		rkisp1_isp_stop(rkisp1);
 		goto mutex_unlock;
-
-	rkisp1_isp_start(rkisp1);
+	}
 
 	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
 			       true);
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 20/55] media: rkisp1: csi: Handle CSI-2 RX configuration fully in rkisp1-csi.c
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP layer now calls multiple functions of the CSI-2 RX layer to
configure, start and stop it, with the steps for the last two
operations. Move those calls to rkisp1_mipi_csi2_start() and
rkisp1_mipi_csi2_stop() to simplify the ISP code and the API exposed by
the CSI-2 receiver component.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 59 +++++++++++--------
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  4 --
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 10 +---
 3 files changed, 35 insertions(+), 38 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 4af04296b625..f19513a601e8 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -18,7 +18,7 @@
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
-int rkisp1_config_mipi(struct rkisp1_csi *csi)
+static int rkisp1_config_mipi(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
@@ -68,6 +68,30 @@ int rkisp1_config_mipi(struct rkisp1_csi *csi)
 	return 0;
 }
 
+void rkisp1_mipi_start(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
+}
+
+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	/* Mask and clear interrupts. */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+}
+
 int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 			   struct rkisp1_sensor_async *sensor)
 {
@@ -75,6 +99,11 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	union phy_configure_opts opts;
 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
 	s64 pixel_clock;
+	int ret;
+
+	ret = rkisp1_config_mipi(csi);
+	if (ret)
+		return ret;
 
 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
 	if (!pixel_clock) {
@@ -89,36 +118,16 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	phy_configure(csi->dphy, &opts);
 	phy_power_on(csi->dphy);
 
+	rkisp1_mipi_start(csi);
+
 	return 0;
 }
 
 void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
 {
-	phy_power_off(csi->dphy);
-}
-
-void rkisp1_mipi_start(struct rkisp1_csi *csi)
-{
-	struct rkisp1_device *rkisp1 = csi->rkisp1;
-	u32 val;
+	rkisp1_mipi_stop(csi);
 
-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
-}
-
-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
-{
-	struct rkisp1_device *rkisp1 = csi->rkisp1;
-	u32 val;
-
-	/* Mask and clear interrupts. */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
-
-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+	phy_power_off(csi->dphy);
 }
 
 irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index d97a4ee5c002..1f921d534865 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -17,12 +17,8 @@ struct rkisp1_sensor_async;
 int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
-int rkisp1_config_mipi(struct rkisp1_csi *csi);
-
 int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 			   struct rkisp1_sensor_async *sensor);
 void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
-void rkisp1_mipi_start(struct rkisp1_csi *csi);
-void rkisp1_mipi_stop(struct rkisp1_csi *csi);
 
 #endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 0e68c8d53404..208c68aa52ea 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -276,7 +276,6 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 		ret = rkisp1_config_dvp(rkisp1);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
-		ret = rkisp1_config_mipi(&rkisp1->csi);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
@@ -309,15 +308,13 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
 	 * ISP(mi) stop in mi frame end -> Stop ISP(mipi) ->
 	 * Stop ISP(isp) ->wait for ISP isp off
 	 */
-	/* stop and clear MI, MIPI, and ISP interrupts */
+	/* stop and clear MI and ISP interrupts */
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
 
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
 
-	rkisp1_mipi_stop(&rkisp1->csi);
-
 	/* stop ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
@@ -358,15 +355,10 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
 
 static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
 {
-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
 	u32 val;
 
 	rkisp1_config_clk(rkisp1);
 
-	/* Activate MIPI */
-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
-		rkisp1_mipi_start(&rkisp1->csi);
-
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 20/55] media: rkisp1: csi: Handle CSI-2 RX configuration fully in rkisp1-csi.c
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP layer now calls multiple functions of the CSI-2 RX layer to
configure, start and stop it, with the steps for the last two
operations. Move those calls to rkisp1_mipi_csi2_start() and
rkisp1_mipi_csi2_stop() to simplify the ISP code and the API exposed by
the CSI-2 receiver component.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 59 +++++++++++--------
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  4 --
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 10 +---
 3 files changed, 35 insertions(+), 38 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 4af04296b625..f19513a601e8 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -18,7 +18,7 @@
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
-int rkisp1_config_mipi(struct rkisp1_csi *csi)
+static int rkisp1_config_mipi(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
@@ -68,6 +68,30 @@ int rkisp1_config_mipi(struct rkisp1_csi *csi)
 	return 0;
 }
 
+void rkisp1_mipi_start(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
+}
+
+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
+{
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	u32 val;
+
+	/* Mask and clear interrupts. */
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
+
+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+}
+
 int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 			   struct rkisp1_sensor_async *sensor)
 {
@@ -75,6 +99,11 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	union phy_configure_opts opts;
 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
 	s64 pixel_clock;
+	int ret;
+
+	ret = rkisp1_config_mipi(csi);
+	if (ret)
+		return ret;
 
 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
 	if (!pixel_clock) {
@@ -89,36 +118,16 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	phy_configure(csi->dphy, &opts);
 	phy_power_on(csi->dphy);
 
+	rkisp1_mipi_start(csi);
+
 	return 0;
 }
 
 void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
 {
-	phy_power_off(csi->dphy);
-}
-
-void rkisp1_mipi_start(struct rkisp1_csi *csi)
-{
-	struct rkisp1_device *rkisp1 = csi->rkisp1;
-	u32 val;
+	rkisp1_mipi_stop(csi);
 
-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
-}
-
-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
-{
-	struct rkisp1_device *rkisp1 = csi->rkisp1;
-	u32 val;
-
-	/* Mask and clear interrupts. */
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
-
-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
+	phy_power_off(csi->dphy);
 }
 
 irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index d97a4ee5c002..1f921d534865 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -17,12 +17,8 @@ struct rkisp1_sensor_async;
 int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
-int rkisp1_config_mipi(struct rkisp1_csi *csi);
-
 int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 			   struct rkisp1_sensor_async *sensor);
 void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
-void rkisp1_mipi_start(struct rkisp1_csi *csi);
-void rkisp1_mipi_stop(struct rkisp1_csi *csi);
 
 #endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 0e68c8d53404..208c68aa52ea 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -276,7 +276,6 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 		ret = rkisp1_config_dvp(rkisp1);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
-		ret = rkisp1_config_mipi(&rkisp1->csi);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
@@ -309,15 +308,13 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
 	 * ISP(mi) stop in mi frame end -> Stop ISP(mipi) ->
 	 * Stop ISP(isp) ->wait for ISP isp off
 	 */
-	/* stop and clear MI, MIPI, and ISP interrupts */
+	/* stop and clear MI and ISP interrupts */
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
 
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
 
-	rkisp1_mipi_stop(&rkisp1->csi);
-
 	/* stop ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
@@ -358,15 +355,10 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
 
 static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
 {
-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
 	u32 val;
 
 	rkisp1_config_clk(rkisp1);
 
-	/* Activate MIPI */
-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
-		rkisp1_mipi_start(&rkisp1->csi);
-
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 21/55] media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi prefix
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The CSI-related functions are not named consistently. Fix it by using a
common rkisp1_csi prefix.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +-
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 20 +++++++++----------
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 +++---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  4 ++--
 .../platform/rockchip/rkisp1/rkisp1-isp.c     |  6 +++---
 5 files changed, 19 insertions(+), 19 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index a52fa9e0dd66..dbf1baca623a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -555,7 +555,7 @@ void rkisp1_params_disable(struct rkisp1_params *params);
 
 /* irq handlers */
 irqreturn_t rkisp1_isp_isr(int irq, void *ctx);
-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx);
+irqreturn_t rkisp1_csi_isr(int irq, void *ctx);
 irqreturn_t rkisp1_capture_isr(int irq, void *ctx);
 void rkisp1_stats_isr(struct rkisp1_stats *stats, u32 isp_ris);
 void rkisp1_params_isr(struct rkisp1_device *rkisp1);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index f19513a601e8..c1bb8c05543d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -18,7 +18,7 @@
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
-static int rkisp1_config_mipi(struct rkisp1_csi *csi)
+static int rkisp1_csi_config(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
@@ -68,7 +68,7 @@ static int rkisp1_config_mipi(struct rkisp1_csi *csi)
 	return 0;
 }
 
-void rkisp1_mipi_start(struct rkisp1_csi *csi)
+static void rkisp1_csi_enable(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	u32 val;
@@ -78,7 +78,7 @@ void rkisp1_mipi_start(struct rkisp1_csi *csi)
 		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
 }
 
-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
+static void rkisp1_csi_disable(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	u32 val;
@@ -92,8 +92,8 @@ void rkisp1_mipi_stop(struct rkisp1_csi *csi)
 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
 }
 
-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
-			   struct rkisp1_sensor_async *sensor)
+int rkisp1_csi_start(struct rkisp1_csi *csi,
+		     struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	union phy_configure_opts opts;
@@ -101,7 +101,7 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	s64 pixel_clock;
 	int ret;
 
-	ret = rkisp1_config_mipi(csi);
+	ret = rkisp1_csi_config(csi);
 	if (ret)
 		return ret;
 
@@ -118,19 +118,19 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	phy_configure(csi->dphy, &opts);
 	phy_power_on(csi->dphy);
 
-	rkisp1_mipi_start(csi);
+	rkisp1_csi_enable(csi);
 
 	return 0;
 }
 
-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
+void rkisp1_csi_stop(struct rkisp1_csi *csi)
 {
-	rkisp1_mipi_stop(csi);
+	rkisp1_csi_disable(csi);
 
 	phy_power_off(csi->dphy);
 }
 
-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
+irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
 {
 	struct device *dev = ctx;
 	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index 1f921d534865..7d3f01cfb49f 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -17,8 +17,8 @@ struct rkisp1_sensor_async;
 int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
-			   struct rkisp1_sensor_async *sensor);
-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
+int rkisp1_csi_start(struct rkisp1_csi *csi,
+		     struct rkisp1_sensor_async *sensor);
+void rkisp1_csi_stop(struct rkisp1_csi *csi);
 
 #endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 373a1f00c10a..253220188abd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -383,7 +383,7 @@ static irqreturn_t rkisp1_isr(int irq, void *ctx)
 	 */
 	rkisp1_capture_isr(irq, ctx);
 	rkisp1_isp_isr(irq, ctx);
-	rkisp1_mipi_isr(irq, ctx);
+	rkisp1_csi_isr(irq, ctx);
 
 	return IRQ_HANDLED;
 }
@@ -398,7 +398,7 @@ static const char * const px30_isp_clks[] = {
 static const struct rkisp1_isr_data px30_isp_isrs[] = {
 	{ "isp", rkisp1_isp_isr },
 	{ "mi", rkisp1_capture_isr },
-	{ "mipi", rkisp1_mipi_isr },
+	{ "mipi", rkisp1_csi_isr },
 };
 
 static const struct rkisp1_info px30_isp_info = {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 208c68aa52ea..ecb8ca0ad670 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -763,7 +763,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
 				 false);
 
-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
+		rkisp1_csi_stop(&rkisp1->csi);
 		rkisp1_isp_stop(rkisp1);
 
 		return 0;
@@ -789,7 +789,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 
 	rkisp1_isp_start(rkisp1);
 
-	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
+	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
 		goto mutex_unlock;
@@ -799,7 +799,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 			       true);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
+		rkisp1_csi_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 21/55] media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi prefix
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The CSI-related functions are not named consistently. Fix it by using a
common rkisp1_csi prefix.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +-
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 20 +++++++++----------
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 +++---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  4 ++--
 .../platform/rockchip/rkisp1/rkisp1-isp.c     |  6 +++---
 5 files changed, 19 insertions(+), 19 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index a52fa9e0dd66..dbf1baca623a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -555,7 +555,7 @@ void rkisp1_params_disable(struct rkisp1_params *params);
 
 /* irq handlers */
 irqreturn_t rkisp1_isp_isr(int irq, void *ctx);
-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx);
+irqreturn_t rkisp1_csi_isr(int irq, void *ctx);
 irqreturn_t rkisp1_capture_isr(int irq, void *ctx);
 void rkisp1_stats_isr(struct rkisp1_stats *stats, u32 isp_ris);
 void rkisp1_params_isr(struct rkisp1_device *rkisp1);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index f19513a601e8..c1bb8c05543d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -18,7 +18,7 @@
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
-static int rkisp1_config_mipi(struct rkisp1_csi *csi)
+static int rkisp1_csi_config(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
@@ -68,7 +68,7 @@ static int rkisp1_config_mipi(struct rkisp1_csi *csi)
 	return 0;
 }
 
-void rkisp1_mipi_start(struct rkisp1_csi *csi)
+static void rkisp1_csi_enable(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	u32 val;
@@ -78,7 +78,7 @@ void rkisp1_mipi_start(struct rkisp1_csi *csi)
 		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
 }
 
-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
+static void rkisp1_csi_disable(struct rkisp1_csi *csi)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	u32 val;
@@ -92,8 +92,8 @@ void rkisp1_mipi_stop(struct rkisp1_csi *csi)
 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
 }
 
-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
-			   struct rkisp1_sensor_async *sensor)
+int rkisp1_csi_start(struct rkisp1_csi *csi,
+		     struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	union phy_configure_opts opts;
@@ -101,7 +101,7 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	s64 pixel_clock;
 	int ret;
 
-	ret = rkisp1_config_mipi(csi);
+	ret = rkisp1_csi_config(csi);
 	if (ret)
 		return ret;
 
@@ -118,19 +118,19 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
 	phy_configure(csi->dphy, &opts);
 	phy_power_on(csi->dphy);
 
-	rkisp1_mipi_start(csi);
+	rkisp1_csi_enable(csi);
 
 	return 0;
 }
 
-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
+void rkisp1_csi_stop(struct rkisp1_csi *csi)
 {
-	rkisp1_mipi_stop(csi);
+	rkisp1_csi_disable(csi);
 
 	phy_power_off(csi->dphy);
 }
 
-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
+irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
 {
 	struct device *dev = ctx;
 	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index 1f921d534865..7d3f01cfb49f 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -17,8 +17,8 @@ struct rkisp1_sensor_async;
 int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
-			   struct rkisp1_sensor_async *sensor);
-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
+int rkisp1_csi_start(struct rkisp1_csi *csi,
+		     struct rkisp1_sensor_async *sensor);
+void rkisp1_csi_stop(struct rkisp1_csi *csi);
 
 #endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 373a1f00c10a..253220188abd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -383,7 +383,7 @@ static irqreturn_t rkisp1_isr(int irq, void *ctx)
 	 */
 	rkisp1_capture_isr(irq, ctx);
 	rkisp1_isp_isr(irq, ctx);
-	rkisp1_mipi_isr(irq, ctx);
+	rkisp1_csi_isr(irq, ctx);
 
 	return IRQ_HANDLED;
 }
@@ -398,7 +398,7 @@ static const char * const px30_isp_clks[] = {
 static const struct rkisp1_isr_data px30_isp_isrs[] = {
 	{ "isp", rkisp1_isp_isr },
 	{ "mi", rkisp1_capture_isr },
-	{ "mipi", rkisp1_mipi_isr },
+	{ "mipi", rkisp1_csi_isr },
 };
 
 static const struct rkisp1_info px30_isp_info = {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 208c68aa52ea..ecb8ca0ad670 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -763,7 +763,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
 				 false);
 
-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
+		rkisp1_csi_stop(&rkisp1->csi);
 		rkisp1_isp_stop(rkisp1);
 
 		return 0;
@@ -789,7 +789,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 
 	rkisp1_isp_start(rkisp1);
 
-	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
+	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
 		goto mutex_unlock;
@@ -799,7 +799,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 			       true);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
+		rkisp1_csi_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 22/55] media: rkisp1: csi: Move start delay to rkisp1_csi_start()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The delay in rkisp1_isp_start() is related to to the CSI-2 receiver and
the camera sensor. Move it where it belongs, to rkisp1_csi_start().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 +++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 6 ------
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index c1bb8c05543d..fcaffffd371b 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -9,6 +9,7 @@
  * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
  */
 
+#include <linux/delay.h>
 #include <linux/device.h>
 #include <linux/phy/phy.h>
 #include <linux/phy/phy-mipi-dphy.h>
@@ -120,6 +121,12 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
 
 	rkisp1_csi_enable(csi);
 
+	/*
+	 * CIF spec says to wait for sufficient time after enabling
+	 * the MIPI interface and before starting the sensor output.
+	 */
+	usleep_range(1000, 1200);
+
 	return 0;
 }
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index ecb8ca0ad670..3ea0deb6b792 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -365,12 +365,6 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
 	       RKISP1_CIF_ISP_CTRL_ISP_ENABLE |
 	       RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE;
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, val);
-
-	/*
-	 * CIF spec says to wait for sufficient time after enabling
-	 * the MIPI interface and before starting the sensor output.
-	 */
-	usleep_range(1000, 1200);
 }
 
 /* ----------------------------------------------------------------------------
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 22/55] media: rkisp1: csi: Move start delay to rkisp1_csi_start()
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The delay in rkisp1_isp_start() is related to to the CSI-2 receiver and
the camera sensor. Move it where it belongs, to rkisp1_csi_start().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 +++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 6 ------
 2 files changed, 7 insertions(+), 6 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index c1bb8c05543d..fcaffffd371b 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -9,6 +9,7 @@
  * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
  */
 
+#include <linux/delay.h>
 #include <linux/device.h>
 #include <linux/phy/phy.h>
 #include <linux/phy/phy-mipi-dphy.h>
@@ -120,6 +121,12 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
 
 	rkisp1_csi_enable(csi);
 
+	/*
+	 * CIF spec says to wait for sufficient time after enabling
+	 * the MIPI interface and before starting the sensor output.
+	 */
+	usleep_range(1000, 1200);
+
 	return 0;
 }
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index ecb8ca0ad670..3ea0deb6b792 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -365,12 +365,6 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
 	       RKISP1_CIF_ISP_CTRL_ISP_ENABLE |
 	       RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE;
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, val);
-
-	/*
-	 * CIF spec says to wait for sufficient time after enabling
-	 * the MIPI interface and before starting the sensor output.
-	 */
-	usleep_range(1000, 1200);
 }
 
 /* ----------------------------------------------------------------------------
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 23/55] media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

To prepare for the removal of the active_sensor field from the
rkisp1_device structure, pass the sensor pointer to the
rkisp1_csi_config() function instead of accessing it through
active_sensor.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index fcaffffd371b..925274b9a3c4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -19,11 +19,12 @@
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
-static int rkisp1_csi_config(struct rkisp1_csi *csi)
+static int rkisp1_csi_config(struct rkisp1_csi *csi,
+			     struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
-	unsigned int lanes = rkisp1->active_sensor->lanes;
+	unsigned int lanes = sensor->lanes;
 	u32 mipi_ctrl;
 
 	if (lanes < 1 || lanes > 4)
@@ -102,7 +103,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
 	s64 pixel_clock;
 	int ret;
 
-	ret = rkisp1_csi_config(csi);
+	ret = rkisp1_csi_config(csi, sensor);
 	if (ret)
 		return ret;
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 23/55] media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

To prepare for the removal of the active_sensor field from the
rkisp1_device structure, pass the sensor pointer to the
rkisp1_csi_config() function instead of accessing it through
active_sensor.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index fcaffffd371b..925274b9a3c4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -19,11 +19,12 @@
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
-static int rkisp1_csi_config(struct rkisp1_csi *csi)
+static int rkisp1_csi_config(struct rkisp1_csi *csi,
+			     struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
-	unsigned int lanes = rkisp1->active_sensor->lanes;
+	unsigned int lanes = sensor->lanes;
 	u32 mipi_ctrl;
 
 	if (lanes < 1 || lanes > 4)
@@ -102,7 +103,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
 	s64 pixel_clock;
 	int ret;
 
-	ret = rkisp1_csi_config(csi);
+	ret = rkisp1_csi_config(csi, sensor);
 	if (ret)
 		return ret;
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 24/55] media: rkisp1: csi: Constify argument to rkisp1_csi_start()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The sensor argument to rkisp1_csi_start() isn't meant to be modified by
the function. Make it const.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 4 ++--
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h | 2 +-
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 925274b9a3c4..425a3b014089 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -20,7 +20,7 @@
 #include "rkisp1-csi.h"
 
 static int rkisp1_csi_config(struct rkisp1_csi *csi,
-			     struct rkisp1_sensor_async *sensor)
+			     const struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
@@ -95,7 +95,7 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
 }
 
 int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     struct rkisp1_sensor_async *sensor)
+		     const struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	union phy_configure_opts opts;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index 7d3f01cfb49f..97ce7e7959ab 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -18,7 +18,7 @@ int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
 int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     struct rkisp1_sensor_async *sensor);
+		     const struct rkisp1_sensor_async *sensor);
 void rkisp1_csi_stop(struct rkisp1_csi *csi);
 
 #endif /* _RKISP1_CSI_H */
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 24/55] media: rkisp1: csi: Constify argument to rkisp1_csi_start()
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The sensor argument to rkisp1_csi_start() isn't meant to be modified by
the function. Make it const.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 4 ++--
 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h | 2 +-
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 925274b9a3c4..425a3b014089 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -20,7 +20,7 @@
 #include "rkisp1-csi.h"
 
 static int rkisp1_csi_config(struct rkisp1_csi *csi,
-			     struct rkisp1_sensor_async *sensor)
+			     const struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
@@ -95,7 +95,7 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
 }
 
 int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     struct rkisp1_sensor_async *sensor)
+		     const struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	union phy_configure_opts opts;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index 7d3f01cfb49f..97ce7e7959ab 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -18,7 +18,7 @@ int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
 int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     struct rkisp1_sensor_async *sensor);
+		     const struct rkisp1_sensor_async *sensor);
 void rkisp1_csi_stop(struct rkisp1_csi *csi);
 
 #endif /* _RKISP1_CSI_H */
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 25/55] media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ret variable doesn't need to be initialized in
rkisp1_isp_s_stream().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 3ea0deb6b792..a234cf29ec67 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -751,7 +751,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = &rkisp1->isp;
 	struct v4l2_subdev *sensor_sd;
-	int ret = 0;
+	int ret;
 
 	if (!enable) {
 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 25/55] media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ret variable doesn't need to be initialized in
rkisp1_isp_s_stream().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 3ea0deb6b792..a234cf29ec67 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -751,7 +751,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = &rkisp1->isp;
 	struct v4l2_subdev *sensor_sd;
-	int ret = 0;
+	int ret;
 
 	if (!enable) {
 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 26/55] media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

To prepare for the removal of the active_sensor field from the
rkisp1_device structure, pass the media bus type of flag to the
rkisp1_config_cif() function instead of accessing them through
active_sensor.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 44 +++++++++----------
 1 file changed, 22 insertions(+), 22 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index a234cf29ec67..f6d1c93dd99d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -136,15 +136,14 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
 /*
  * configure ISP blocks with input format, size......
  */
-static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
+static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
-	struct rkisp1_sensor_async *sensor;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
 
-	sensor = rkisp1->active_sensor;
 	sink_fmt = rkisp1->isp.sink_fmt;
 	src_fmt = rkisp1->isp.src_fmt;
 	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
@@ -157,7 +156,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 	if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
 		acq_mult = 1;
 		if (src_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
-			if (sensor->mbus_type == V4L2_MBUS_BT656)
+			if (mbus_type == V4L2_MBUS_BT656)
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT_ITU656;
 			else
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT;
@@ -165,17 +164,17 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 			rkisp1_write(rkisp1, RKISP1_CIF_ISP_DEMOSAIC,
 				     RKISP1_CIF_ISP_DEMOSAIC_TH(0xc));
 
-			if (sensor->mbus_type == V4L2_MBUS_BT656)
+			if (mbus_type == V4L2_MBUS_BT656)
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU656;
 			else
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU601;
 		}
 	} else if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_YUV) {
 		acq_mult = 2;
-		if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
+		if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 			isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
 		} else {
-			if (sensor->mbus_type == V4L2_MBUS_BT656)
+			if (mbus_type == V4L2_MBUS_BT656)
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU656;
 			else
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
@@ -185,17 +184,16 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 	}
 
 	/* Set up input acquisition properties */
-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
-		if (sensor->mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
+		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
 	}
 
-	if (sensor->mbus_type == V4L2_MBUS_PARALLEL) {
-		if (sensor->mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
+	if (mbus_type == V4L2_MBUS_PARALLEL) {
+		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
 			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
 
-		if (sensor->mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
+		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
 			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
 	}
 
@@ -265,17 +263,17 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 }
 
 /* Configure MUX */
-static int rkisp1_config_path(struct rkisp1_device *rkisp1)
+static int rkisp1_config_path(struct rkisp1_device *rkisp1,
+			      enum v4l2_mbus_type mbus_type)
 {
-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
 	int ret = 0;
 
-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
+	if (mbus_type == V4L2_MBUS_BT656 ||
+	    mbus_type == V4L2_MBUS_PARALLEL) {
 		ret = rkisp1_config_dvp(rkisp1);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
-	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
+	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
@@ -285,14 +283,15 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 }
 
 /* Hardware configure Entry */
-static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
+static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	int ret;
 
-	ret = rkisp1_config_isp(rkisp1);
+	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
 	if (ret)
 		return ret;
-	ret = rkisp1_config_path(rkisp1);
+	ret = rkisp1_config_path(rkisp1, mbus_type);
 	if (ret)
 		return ret;
 	rkisp1_config_ism(rkisp1);
@@ -777,7 +776,8 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 
 	rkisp1->isp.frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(rkisp1);
+	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
+				rkisp1->active_sensor->mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 26/55] media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

To prepare for the removal of the active_sensor field from the
rkisp1_device structure, pass the media bus type of flag to the
rkisp1_config_cif() function instead of accessing them through
active_sensor.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 44 +++++++++----------
 1 file changed, 22 insertions(+), 22 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index a234cf29ec67..f6d1c93dd99d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -136,15 +136,14 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
 /*
  * configure ISP blocks with input format, size......
  */
-static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
+static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
-	struct rkisp1_sensor_async *sensor;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
 
-	sensor = rkisp1->active_sensor;
 	sink_fmt = rkisp1->isp.sink_fmt;
 	src_fmt = rkisp1->isp.src_fmt;
 	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
@@ -157,7 +156,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 	if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
 		acq_mult = 1;
 		if (src_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
-			if (sensor->mbus_type == V4L2_MBUS_BT656)
+			if (mbus_type == V4L2_MBUS_BT656)
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT_ITU656;
 			else
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT;
@@ -165,17 +164,17 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 			rkisp1_write(rkisp1, RKISP1_CIF_ISP_DEMOSAIC,
 				     RKISP1_CIF_ISP_DEMOSAIC_TH(0xc));
 
-			if (sensor->mbus_type == V4L2_MBUS_BT656)
+			if (mbus_type == V4L2_MBUS_BT656)
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU656;
 			else
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU601;
 		}
 	} else if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_YUV) {
 		acq_mult = 2;
-		if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
+		if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 			isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
 		} else {
-			if (sensor->mbus_type == V4L2_MBUS_BT656)
+			if (mbus_type == V4L2_MBUS_BT656)
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU656;
 			else
 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
@@ -185,17 +184,16 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
 	}
 
 	/* Set up input acquisition properties */
-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
-		if (sensor->mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
+		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
 	}
 
-	if (sensor->mbus_type == V4L2_MBUS_PARALLEL) {
-		if (sensor->mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
+	if (mbus_type == V4L2_MBUS_PARALLEL) {
+		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
 			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
 
-		if (sensor->mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
+		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
 			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
 	}
 
@@ -265,17 +263,17 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 }
 
 /* Configure MUX */
-static int rkisp1_config_path(struct rkisp1_device *rkisp1)
+static int rkisp1_config_path(struct rkisp1_device *rkisp1,
+			      enum v4l2_mbus_type mbus_type)
 {
-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
 	int ret = 0;
 
-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
+	if (mbus_type == V4L2_MBUS_BT656 ||
+	    mbus_type == V4L2_MBUS_PARALLEL) {
 		ret = rkisp1_config_dvp(rkisp1);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
-	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
+	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
@@ -285,14 +283,15 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
 }
 
 /* Hardware configure Entry */
-static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
+static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	int ret;
 
-	ret = rkisp1_config_isp(rkisp1);
+	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
 	if (ret)
 		return ret;
-	ret = rkisp1_config_path(rkisp1);
+	ret = rkisp1_config_path(rkisp1, mbus_type);
 	if (ret)
 		return ret;
 	rkisp1_config_ism(rkisp1);
@@ -777,7 +776,8 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 
 	rkisp1->isp.frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(rkisp1);
+	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
+				rkisp1->active_sensor->mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:10   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The active_sensor field of the rkisp1_device structure points to the ASD
data for the active source. The source may however not be a sensor, so
the naming is a bit confusing. Furthermore, the driver doesn't need to
access the full ASD from the active_sensor field, only the subdev
pointer is needed, when stopping streaming.

Rename the field to source, and turn it into a v4l2_subdev pointer.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  4 +--
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 27 +++++++++----------
 2 files changed, 14 insertions(+), 17 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index dbf1baca623a..7a6f55a31bb0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -419,7 +419,7 @@ struct rkisp1_debug {
  * @v4l2_dev:	   v4l2_device variable
  * @media_dev:	   media_device variable
  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
- * @active_sensor: sensor in-use, set when streaming on
+ * @source:        source subdev in-use, set when starting streaming
  * @csi:	   internal CSI-2 receiver
  * @isp:	   ISP sub-device
  * @resizer_devs:  resizer sub-devices
@@ -439,7 +439,7 @@ struct rkisp1_device {
 	struct v4l2_device v4l2_dev;
 	struct media_device media_dev;
 	struct v4l2_async_notifier notifier;
-	struct rkisp1_sensor_async *active_sensor;
+	struct v4l2_subdev *source;
 	struct rkisp1_csi csi;
 	struct rkisp1_isp isp;
 	struct rkisp1_resizer resizer_devs[2];
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index f6d1c93dd99d..4f12fc0b7694 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -58,7 +58,7 @@
  * Helpers
  */
 
-static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
+static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
 {
 	struct media_pad *local, *remote;
 	struct media_entity *sensor_me;
@@ -749,12 +749,11 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	struct rkisp1_device *rkisp1 =
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = &rkisp1->isp;
-	struct v4l2_subdev *sensor_sd;
+	struct rkisp1_sensor_async *asd;
 	int ret;
 
 	if (!enable) {
-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-				 false);
+		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
 
 		rkisp1_csi_stop(&rkisp1->csi);
 		rkisp1_isp_stop(rkisp1);
@@ -762,35 +761,33 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return 0;
 	}
 
-	sensor_sd = rkisp1_get_remote_sensor(sd);
-	if (!sensor_sd) {
-		dev_warn(rkisp1->dev, "No link between isp and sensor\n");
+	rkisp1->source = rkisp1_get_remote_source(sd);
+	if (!rkisp1->source) {
+		dev_warn(rkisp1->dev, "No link between isp and source\n");
 		return -ENODEV;
 	}
 
-	rkisp1->active_sensor = container_of(sensor_sd->asd,
-					     struct rkisp1_sensor_async, asd);
+	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
+			   asd);
 
-	if (rkisp1->active_sensor->mbus_type != V4L2_MBUS_CSI2_DPHY)
+	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
 		return -EINVAL;
 
 	rkisp1->isp.frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
-				rkisp1->active_sensor->mbus_flags);
+	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
 	rkisp1_isp_start(rkisp1);
 
-	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
+	ret = rkisp1_csi_start(&rkisp1->csi, asd);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
 		goto mutex_unlock;
 	}
 
-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-			       true);
+	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
 		rkisp1_csi_stop(&rkisp1->csi);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
@ 2022-06-14 19:10   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:10 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The active_sensor field of the rkisp1_device structure points to the ASD
data for the active source. The source may however not be a sensor, so
the naming is a bit confusing. Furthermore, the driver doesn't need to
access the full ASD from the active_sensor field, only the subdev
pointer is needed, when stopping streaming.

Rename the field to source, and turn it into a v4l2_subdev pointer.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  4 +--
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 27 +++++++++----------
 2 files changed, 14 insertions(+), 17 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index dbf1baca623a..7a6f55a31bb0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -419,7 +419,7 @@ struct rkisp1_debug {
  * @v4l2_dev:	   v4l2_device variable
  * @media_dev:	   media_device variable
  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
- * @active_sensor: sensor in-use, set when streaming on
+ * @source:        source subdev in-use, set when starting streaming
  * @csi:	   internal CSI-2 receiver
  * @isp:	   ISP sub-device
  * @resizer_devs:  resizer sub-devices
@@ -439,7 +439,7 @@ struct rkisp1_device {
 	struct v4l2_device v4l2_dev;
 	struct media_device media_dev;
 	struct v4l2_async_notifier notifier;
-	struct rkisp1_sensor_async *active_sensor;
+	struct v4l2_subdev *source;
 	struct rkisp1_csi csi;
 	struct rkisp1_isp isp;
 	struct rkisp1_resizer resizer_devs[2];
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index f6d1c93dd99d..4f12fc0b7694 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -58,7 +58,7 @@
  * Helpers
  */
 
-static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
+static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
 {
 	struct media_pad *local, *remote;
 	struct media_entity *sensor_me;
@@ -749,12 +749,11 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	struct rkisp1_device *rkisp1 =
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = &rkisp1->isp;
-	struct v4l2_subdev *sensor_sd;
+	struct rkisp1_sensor_async *asd;
 	int ret;
 
 	if (!enable) {
-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-				 false);
+		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
 
 		rkisp1_csi_stop(&rkisp1->csi);
 		rkisp1_isp_stop(rkisp1);
@@ -762,35 +761,33 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return 0;
 	}
 
-	sensor_sd = rkisp1_get_remote_sensor(sd);
-	if (!sensor_sd) {
-		dev_warn(rkisp1->dev, "No link between isp and sensor\n");
+	rkisp1->source = rkisp1_get_remote_source(sd);
+	if (!rkisp1->source) {
+		dev_warn(rkisp1->dev, "No link between isp and source\n");
 		return -ENODEV;
 	}
 
-	rkisp1->active_sensor = container_of(sensor_sd->asd,
-					     struct rkisp1_sensor_async, asd);
+	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
+			   asd);
 
-	if (rkisp1->active_sensor->mbus_type != V4L2_MBUS_CSI2_DPHY)
+	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
 		return -EINVAL;
 
 	rkisp1->isp.frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
-				rkisp1->active_sensor->mbus_flags);
+	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
 	rkisp1_isp_start(rkisp1);
 
-	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
+	ret = rkisp1_csi_start(&rkisp1->csi, asd);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
 		goto mutex_unlock;
 	}
 
-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
-			       true);
+	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
 		rkisp1_isp_stop(rkisp1);
 		rkisp1_csi_stop(&rkisp1->csi);
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 28/55] media: rkisp1: isp: Add container_of wrapper to cast subdev to rkisp1_isp
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Replace manual container_of() calls with a static inline wrapper to
increase readability.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-isp.c   | 15 ++++++++++-----
 1 file changed, 10 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 4f12fc0b7694..812fb2ea5323 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -370,6 +370,11 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
  * Subdev pad operations
  */
 
+static inline struct rkisp1_isp *to_rkisp1_isp(struct v4l2_subdev *sd)
+{
+	return container_of(sd, struct rkisp1_isp, sd);
+}
+
 static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
 				     struct v4l2_subdev_state *sd_state,
 				     struct v4l2_subdev_mbus_code_enum *code)
@@ -625,7 +630,7 @@ static int rkisp1_isp_get_fmt(struct v4l2_subdev *sd,
 			      struct v4l2_subdev_state *sd_state,
 			      struct v4l2_subdev_format *fmt)
 {
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 
 	mutex_lock(&isp->ops_lock);
 	fmt->format = *rkisp1_isp_get_pad_fmt(isp, sd_state, fmt->pad,
@@ -638,7 +643,7 @@ static int rkisp1_isp_set_fmt(struct v4l2_subdev *sd,
 			      struct v4l2_subdev_state *sd_state,
 			      struct v4l2_subdev_format *fmt)
 {
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 
 	mutex_lock(&isp->ops_lock);
 	if (fmt->pad == RKISP1_ISP_PAD_SINK_VIDEO)
@@ -659,7 +664,7 @@ static int rkisp1_isp_get_selection(struct v4l2_subdev *sd,
 				    struct v4l2_subdev_state *sd_state,
 				    struct v4l2_subdev_selection *sel)
 {
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	int ret = 0;
 
 	if (sel->pad != RKISP1_ISP_PAD_SOURCE_VIDEO &&
@@ -701,7 +706,7 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
 {
 	struct rkisp1_device *rkisp1 =
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	int ret = 0;
 
 	if (sel->target != V4L2_SEL_TGT_CROP)
@@ -748,7 +753,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_device *rkisp1 =
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
-	struct rkisp1_isp *isp = &rkisp1->isp;
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_sensor_async *asd;
 	int ret;
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 28/55] media: rkisp1: isp: Add container_of wrapper to cast subdev to rkisp1_isp
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Replace manual container_of() calls with a static inline wrapper to
increase readability.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-isp.c   | 15 ++++++++++-----
 1 file changed, 10 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 4f12fc0b7694..812fb2ea5323 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -370,6 +370,11 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
  * Subdev pad operations
  */
 
+static inline struct rkisp1_isp *to_rkisp1_isp(struct v4l2_subdev *sd)
+{
+	return container_of(sd, struct rkisp1_isp, sd);
+}
+
 static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
 				     struct v4l2_subdev_state *sd_state,
 				     struct v4l2_subdev_mbus_code_enum *code)
@@ -625,7 +630,7 @@ static int rkisp1_isp_get_fmt(struct v4l2_subdev *sd,
 			      struct v4l2_subdev_state *sd_state,
 			      struct v4l2_subdev_format *fmt)
 {
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 
 	mutex_lock(&isp->ops_lock);
 	fmt->format = *rkisp1_isp_get_pad_fmt(isp, sd_state, fmt->pad,
@@ -638,7 +643,7 @@ static int rkisp1_isp_set_fmt(struct v4l2_subdev *sd,
 			      struct v4l2_subdev_state *sd_state,
 			      struct v4l2_subdev_format *fmt)
 {
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 
 	mutex_lock(&isp->ops_lock);
 	if (fmt->pad == RKISP1_ISP_PAD_SINK_VIDEO)
@@ -659,7 +664,7 @@ static int rkisp1_isp_get_selection(struct v4l2_subdev *sd,
 				    struct v4l2_subdev_state *sd_state,
 				    struct v4l2_subdev_selection *sel)
 {
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	int ret = 0;
 
 	if (sel->pad != RKISP1_ISP_PAD_SOURCE_VIDEO &&
@@ -701,7 +706,7 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
 {
 	struct rkisp1_device *rkisp1 =
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	int ret = 0;
 
 	if (sel->target != V4L2_SEL_TGT_CROP)
@@ -748,7 +753,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_device *rkisp1 =
 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
-	struct rkisp1_isp *isp = &rkisp1->isp;
+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_sensor_async *asd;
 	int ret;
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 29/55] media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1_isp structure documentation mentions a backpointer field to
rkisp1_device, but the field is missing. Add it, and use it to replace
more complicated constructs using container_of() on the v4l2_device.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-common.h    |  1 +
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c   | 11 +++++------
 2 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 7a6f55a31bb0..3c55e922346e 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -162,6 +162,7 @@ struct rkisp1_csi {
  */
 struct rkisp1_isp {
 	struct v4l2_subdev sd;
+	struct rkisp1_device *rkisp1;
 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
 	const struct rkisp1_mbus_info *sink_fmt;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 812fb2ea5323..f8ab1d9cc8cd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -704,15 +704,13 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
 				    struct v4l2_subdev_state *sd_state,
 				    struct v4l2_subdev_selection *sel)
 {
-	struct rkisp1_device *rkisp1 =
-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	int ret = 0;
 
 	if (sel->target != V4L2_SEL_TGT_CROP)
 		return -EINVAL;
 
-	dev_dbg(rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
+	dev_dbg(isp->rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
 		sel->pad, sel->r.left, sel->r.top, sel->r.width, sel->r.height);
 	mutex_lock(&isp->ops_lock);
 	if (sel->pad == RKISP1_ISP_PAD_SINK_VIDEO)
@@ -751,9 +749,8 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
 
 static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
-	struct rkisp1_device *rkisp1 =
-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	struct rkisp1_sensor_async *asd;
 	int ret;
 
@@ -840,12 +837,14 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_subdev_state state = {
 		.pads = rkisp1->isp.pad_cfg
-		};
+	};
 	struct rkisp1_isp *isp = &rkisp1->isp;
 	struct media_pad *pads = isp->pads;
 	struct v4l2_subdev *sd = &isp->sd;
 	int ret;
 
+	isp->rkisp1 = rkisp1;
+
 	v4l2_subdev_init(sd, &rkisp1_isp_ops);
 	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE | V4L2_SUBDEV_FL_HAS_EVENTS;
 	sd->entity.ops = &rkisp1_isp_media_ops;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 29/55] media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1_isp structure documentation mentions a backpointer field to
rkisp1_device, but the field is missing. Add it, and use it to replace
more complicated constructs using container_of() on the v4l2_device.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-common.h    |  1 +
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c   | 11 +++++------
 2 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 7a6f55a31bb0..3c55e922346e 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -162,6 +162,7 @@ struct rkisp1_csi {
  */
 struct rkisp1_isp {
 	struct v4l2_subdev sd;
+	struct rkisp1_device *rkisp1;
 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
 	const struct rkisp1_mbus_info *sink_fmt;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 812fb2ea5323..f8ab1d9cc8cd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -704,15 +704,13 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
 				    struct v4l2_subdev_state *sd_state,
 				    struct v4l2_subdev_selection *sel)
 {
-	struct rkisp1_device *rkisp1 =
-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	int ret = 0;
 
 	if (sel->target != V4L2_SEL_TGT_CROP)
 		return -EINVAL;
 
-	dev_dbg(rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
+	dev_dbg(isp->rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
 		sel->pad, sel->r.left, sel->r.top, sel->r.width, sel->r.height);
 	mutex_lock(&isp->ops_lock);
 	if (sel->pad == RKISP1_ISP_PAD_SINK_VIDEO)
@@ -751,9 +749,8 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
 
 static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
-	struct rkisp1_device *rkisp1 =
-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	struct rkisp1_sensor_async *asd;
 	int ret;
 
@@ -840,12 +837,14 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_subdev_state state = {
 		.pads = rkisp1->isp.pad_cfg
-		};
+	};
 	struct rkisp1_isp *isp = &rkisp1->isp;
 	struct media_pad *pads = isp->pads;
 	struct v4l2_subdev *sd = &isp->sd;
 	int ret;
 
+	isp->rkisp1 = rkisp1;
+
 	v4l2_subdev_init(sd, &rkisp1_isp_ops);
 	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE | V4L2_SUBDEV_FL_HAS_EVENTS;
 	sd->entity.ops = &rkisp1_isp_media_ops;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 30/55] media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Replace the rkisp1_device pointer argument to the internal functions of
the ISP implementation with a rkisp1_isp object. This makes the code
flow more logical, as the functions operate on the ISP object.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 60 +++++++++++--------
 1 file changed, 34 insertions(+), 26 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index f8ab1d9cc8cd..e27137b5c33e 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -109,12 +109,13 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
  * This should only be called when configuring CIF
  * or at the frame end interrupt
  */
-static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
+static void rkisp1_config_ism(struct rkisp1_isp *isp)
 {
 	struct v4l2_rect *src_crop =
-		rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
+		rkisp1_isp_get_pad_crop(isp, NULL,
 					RKISP1_ISP_PAD_SOURCE_VIDEO,
 					V4L2_SUBDEV_FORMAT_ACTIVE);
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
 
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IS_RECENTER, 0);
@@ -136,20 +137,21 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
 /*
  * configure ISP blocks with input format, size......
  */
-static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
+static int rkisp1_config_isp(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
 
-	sink_fmt = rkisp1->isp.sink_fmt;
-	src_fmt = rkisp1->isp.src_fmt;
-	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
+	sink_fmt = isp->sink_fmt;
+	src_fmt = isp->src_fmt;
+	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
 					  V4L2_SUBDEV_FORMAT_ACTIVE);
-	sink_crop = rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
+	sink_crop = rkisp1_isp_get_pad_crop(isp, NULL,
 					    RKISP1_ISP_PAD_SINK_VIDEO,
 					    V4L2_SUBDEV_FORMAT_ACTIVE);
 
@@ -226,7 +228,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
 	} else {
 		struct v4l2_mbus_framefmt *src_frm;
 
-		src_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
+		src_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 						 RKISP1_ISP_PAD_SINK_VIDEO,
 						 V4L2_SUBDEV_FORMAT_ACTIVE);
 		rkisp1_params_configure(&rkisp1->params, sink_fmt->bayer_pat,
@@ -236,9 +238,10 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
 	return 0;
 }
 
-static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
+static int rkisp1_config_dvp(struct rkisp1_isp *isp)
 {
-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
 	u32 val, input_sel;
 
 	switch (sink_fmt->bus_width) {
@@ -263,15 +266,16 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 }
 
 /* Configure MUX */
-static int rkisp1_config_path(struct rkisp1_device *rkisp1,
+static int rkisp1_config_path(struct rkisp1_isp *isp,
 			      enum v4l2_mbus_type mbus_type)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
 	int ret = 0;
 
 	if (mbus_type == V4L2_MBUS_BT656 ||
 	    mbus_type == V4L2_MBUS_PARALLEL) {
-		ret = rkisp1_config_dvp(rkisp1);
+		ret = rkisp1_config_dvp(isp);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
@@ -283,24 +287,25 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1,
 }
 
 /* Hardware configure Entry */
-static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
+static int rkisp1_config_cif(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	int ret;
 
-	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
+	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
 	if (ret)
 		return ret;
-	ret = rkisp1_config_path(rkisp1, mbus_type);
+	ret = rkisp1_config_path(isp, mbus_type);
 	if (ret)
 		return ret;
-	rkisp1_config_ism(rkisp1);
+	rkisp1_config_ism(isp);
 
 	return 0;
 }
 
-static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
+static void rkisp1_isp_stop(struct rkisp1_isp *isp)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
 
 	/*
@@ -332,8 +337,10 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_IRCL, 0x0);
 }
 
-static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
+static void rkisp1_config_clk(struct rkisp1_isp *isp)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
+
 	u32 val = RKISP1_CIF_VI_ICCL_ISP_CLK | RKISP1_CIF_VI_ICCL_CP_CLK |
 		  RKISP1_CIF_VI_ICCL_MRSZ_CLK | RKISP1_CIF_VI_ICCL_SRSZ_CLK |
 		  RKISP1_CIF_VI_ICCL_JPEG_CLK | RKISP1_CIF_VI_ICCL_MI_CLK |
@@ -352,11 +359,12 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
 	}
 }
 
-static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
+static void rkisp1_isp_start(struct rkisp1_isp *isp)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
 
-	rkisp1_config_clk(rkisp1);
+	rkisp1_config_clk(isp);
 
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
@@ -758,7 +766,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
 
 		rkisp1_csi_stop(&rkisp1->csi);
-		rkisp1_isp_stop(rkisp1);
+		rkisp1_isp_stop(isp);
 
 		return 0;
 	}
@@ -775,23 +783,23 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
 		return -EINVAL;
 
-	rkisp1->isp.frame_sequence = -1;
+	isp->frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
+	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
-	rkisp1_isp_start(rkisp1);
+	rkisp1_isp_start(isp);
 
 	ret = rkisp1_csi_start(&rkisp1->csi, asd);
 	if (ret) {
-		rkisp1_isp_stop(rkisp1);
+		rkisp1_isp_stop(isp);
 		goto mutex_unlock;
 	}
 
 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
-		rkisp1_isp_stop(rkisp1);
+		rkisp1_isp_stop(isp);
 		rkisp1_csi_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 30/55] media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Replace the rkisp1_device pointer argument to the internal functions of
the ISP implementation with a rkisp1_isp object. This makes the code
flow more logical, as the functions operate on the ISP object.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 60 +++++++++++--------
 1 file changed, 34 insertions(+), 26 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index f8ab1d9cc8cd..e27137b5c33e 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -109,12 +109,13 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
  * This should only be called when configuring CIF
  * or at the frame end interrupt
  */
-static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
+static void rkisp1_config_ism(struct rkisp1_isp *isp)
 {
 	struct v4l2_rect *src_crop =
-		rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
+		rkisp1_isp_get_pad_crop(isp, NULL,
 					RKISP1_ISP_PAD_SOURCE_VIDEO,
 					V4L2_SUBDEV_FORMAT_ACTIVE);
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
 
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IS_RECENTER, 0);
@@ -136,20 +137,21 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
 /*
  * configure ISP blocks with input format, size......
  */
-static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
+static int rkisp1_config_isp(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
 
-	sink_fmt = rkisp1->isp.sink_fmt;
-	src_fmt = rkisp1->isp.src_fmt;
-	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
+	sink_fmt = isp->sink_fmt;
+	src_fmt = isp->src_fmt;
+	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
 					  V4L2_SUBDEV_FORMAT_ACTIVE);
-	sink_crop = rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
+	sink_crop = rkisp1_isp_get_pad_crop(isp, NULL,
 					    RKISP1_ISP_PAD_SINK_VIDEO,
 					    V4L2_SUBDEV_FORMAT_ACTIVE);
 
@@ -226,7 +228,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
 	} else {
 		struct v4l2_mbus_framefmt *src_frm;
 
-		src_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
+		src_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 						 RKISP1_ISP_PAD_SINK_VIDEO,
 						 V4L2_SUBDEV_FORMAT_ACTIVE);
 		rkisp1_params_configure(&rkisp1->params, sink_fmt->bayer_pat,
@@ -236,9 +238,10 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
 	return 0;
 }
 
-static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
+static int rkisp1_config_dvp(struct rkisp1_isp *isp)
 {
-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
 	u32 val, input_sel;
 
 	switch (sink_fmt->bus_width) {
@@ -263,15 +266,16 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
 }
 
 /* Configure MUX */
-static int rkisp1_config_path(struct rkisp1_device *rkisp1,
+static int rkisp1_config_path(struct rkisp1_isp *isp,
 			      enum v4l2_mbus_type mbus_type)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
 	int ret = 0;
 
 	if (mbus_type == V4L2_MBUS_BT656 ||
 	    mbus_type == V4L2_MBUS_PARALLEL) {
-		ret = rkisp1_config_dvp(rkisp1);
+		ret = rkisp1_config_dvp(isp);
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
@@ -283,24 +287,25 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1,
 }
 
 /* Hardware configure Entry */
-static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
+static int rkisp1_config_cif(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	int ret;
 
-	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
+	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
 	if (ret)
 		return ret;
-	ret = rkisp1_config_path(rkisp1, mbus_type);
+	ret = rkisp1_config_path(isp, mbus_type);
 	if (ret)
 		return ret;
-	rkisp1_config_ism(rkisp1);
+	rkisp1_config_ism(isp);
 
 	return 0;
 }
 
-static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
+static void rkisp1_isp_stop(struct rkisp1_isp *isp)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
 
 	/*
@@ -332,8 +337,10 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_IRCL, 0x0);
 }
 
-static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
+static void rkisp1_config_clk(struct rkisp1_isp *isp)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
+
 	u32 val = RKISP1_CIF_VI_ICCL_ISP_CLK | RKISP1_CIF_VI_ICCL_CP_CLK |
 		  RKISP1_CIF_VI_ICCL_MRSZ_CLK | RKISP1_CIF_VI_ICCL_SRSZ_CLK |
 		  RKISP1_CIF_VI_ICCL_JPEG_CLK | RKISP1_CIF_VI_ICCL_MI_CLK |
@@ -352,11 +359,12 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
 	}
 }
 
-static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
+static void rkisp1_isp_start(struct rkisp1_isp *isp)
 {
+	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
 
-	rkisp1_config_clk(rkisp1);
+	rkisp1_config_clk(isp);
 
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
@@ -758,7 +766,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
 
 		rkisp1_csi_stop(&rkisp1->csi);
-		rkisp1_isp_stop(rkisp1);
+		rkisp1_isp_stop(isp);
 
 		return 0;
 	}
@@ -775,23 +783,23 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
 		return -EINVAL;
 
-	rkisp1->isp.frame_sequence = -1;
+	isp->frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
+	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
-	rkisp1_isp_start(rkisp1);
+	rkisp1_isp_start(isp);
 
 	ret = rkisp1_csi_start(&rkisp1->csi, asd);
 	if (ret) {
-		rkisp1_isp_stop(rkisp1);
+		rkisp1_isp_stop(isp);
 		goto mutex_unlock;
 	}
 
 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
-		rkisp1_isp_stop(rkisp1);
+		rkisp1_isp_stop(isp);
 		rkisp1_csi_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 31/55] media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP_ACQ_PROP register is set twice, once in rkisp1_config_isp() for
most of its fields, and once in rkisp1_config_dvp() (called from
rkisp1_config_path()) to configure the input selection field. Move the
latter to rkisp1_config_isp() to write the register once only, and drop
the now empty rkisp1_config_dvp() function.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 62 +++++++------------
 1 file changed, 22 insertions(+), 40 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index e27137b5c33e..f5b8a2e31936 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
@@ -189,6 +189,21 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
+
+		switch (sink_fmt->bus_width) {
+		case 8:
+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
+			break;
+		case 10:
+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
+			break;
+		case 12:
+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
+			break;
+		default:
+			dev_err(rkisp1->dev, "Invalid bus width\n");
+			return -EINVAL;
+		}
 	}
 
 	if (mbus_type == V4L2_MBUS_PARALLEL) {
@@ -201,7 +216,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
-		     signal | sink_fmt->yuv_seq |
+		     signal | sink_fmt->yuv_seq | input_sel |
 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
@@ -238,52 +253,20 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	return 0;
 }
 
-static int rkisp1_config_dvp(struct rkisp1_isp *isp)
-{
-	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
-	u32 val, input_sel;
-
-	switch (sink_fmt->bus_width) {
-	case 8:
-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
-		break;
-	case 10:
-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
-		break;
-	case 12:
-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
-		break;
-	default:
-		dev_err(rkisp1->dev, "Invalid bus width\n");
-		return -EINVAL;
-	}
-
-	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_ACQ_PROP);
-	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP, val | input_sel);
-
-	return 0;
-}
-
 /* Configure MUX */
-static int rkisp1_config_path(struct rkisp1_isp *isp,
-			      enum v4l2_mbus_type mbus_type)
+static void rkisp1_config_path(struct rkisp1_isp *isp,
+			       enum v4l2_mbus_type mbus_type)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
-	int ret = 0;
 
-	if (mbus_type == V4L2_MBUS_BT656 ||
-	    mbus_type == V4L2_MBUS_PARALLEL) {
-		ret = rkisp1_config_dvp(isp);
+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_DPCL, dpcl);
-
-	return ret;
 }
 
 /* Hardware configure Entry */
@@ -295,9 +278,8 @@ static int rkisp1_config_cif(struct rkisp1_isp *isp,
 	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
 	if (ret)
 		return ret;
-	ret = rkisp1_config_path(isp, mbus_type);
-	if (ret)
-		return ret;
+
+	rkisp1_config_path(isp, mbus_type);
 	rkisp1_config_ism(isp);
 
 	return 0;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 31/55] media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP_ACQ_PROP register is set twice, once in rkisp1_config_isp() for
most of its fields, and once in rkisp1_config_dvp() (called from
rkisp1_config_path()) to configure the input selection field. Move the
latter to rkisp1_config_isp() to write the register once only, and drop
the now empty rkisp1_config_dvp() function.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 62 +++++++------------
 1 file changed, 22 insertions(+), 40 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index e27137b5c33e..f5b8a2e31936 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
@@ -189,6 +189,21 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
+
+		switch (sink_fmt->bus_width) {
+		case 8:
+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
+			break;
+		case 10:
+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
+			break;
+		case 12:
+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
+			break;
+		default:
+			dev_err(rkisp1->dev, "Invalid bus width\n");
+			return -EINVAL;
+		}
 	}
 
 	if (mbus_type == V4L2_MBUS_PARALLEL) {
@@ -201,7 +216,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
-		     signal | sink_fmt->yuv_seq |
+		     signal | sink_fmt->yuv_seq | input_sel |
 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
@@ -238,52 +253,20 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	return 0;
 }
 
-static int rkisp1_config_dvp(struct rkisp1_isp *isp)
-{
-	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
-	u32 val, input_sel;
-
-	switch (sink_fmt->bus_width) {
-	case 8:
-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
-		break;
-	case 10:
-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
-		break;
-	case 12:
-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
-		break;
-	default:
-		dev_err(rkisp1->dev, "Invalid bus width\n");
-		return -EINVAL;
-	}
-
-	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_ACQ_PROP);
-	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP, val | input_sel);
-
-	return 0;
-}
-
 /* Configure MUX */
-static int rkisp1_config_path(struct rkisp1_isp *isp,
-			      enum v4l2_mbus_type mbus_type)
+static void rkisp1_config_path(struct rkisp1_isp *isp,
+			       enum v4l2_mbus_type mbus_type)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
-	int ret = 0;
 
-	if (mbus_type == V4L2_MBUS_BT656 ||
-	    mbus_type == V4L2_MBUS_PARALLEL) {
-		ret = rkisp1_config_dvp(isp);
+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
 	}
 
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_DPCL, dpcl);
-
-	return ret;
 }
 
 /* Hardware configure Entry */
@@ -295,9 +278,8 @@ static int rkisp1_config_cif(struct rkisp1_isp *isp,
 	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
 	if (ret)
 		return ret;
-	ret = rkisp1_config_path(isp, mbus_type);
-	if (ret)
-		return ret;
+
+	rkisp1_config_path(isp, mbus_type);
 	rkisp1_config_ism(isp);
 
 	return 0;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 32/55] media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single variable
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1_config_isp() function stores the value of the input selection
and polarity configuration in two different local variables, OR'ed
together when writing the register. Merge them into a single acq_prop
variable.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-isp.c  | 16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index f5b8a2e31936..4496af991c82 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
@@ -188,17 +188,17 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	/* Set up input acquisition properties */
 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
-			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
 
 		switch (sink_fmt->bus_width) {
 		case 8:
-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
 			break;
 		case 10:
-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
 			break;
 		case 12:
-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
 			break;
 		default:
 			dev_err(rkisp1->dev, "Invalid bus width\n");
@@ -208,15 +208,15 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 
 	if (mbus_type == V4L2_MBUS_PARALLEL) {
 		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
-			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
 
 		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
-			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
 	}
 
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
-		     signal | sink_fmt->yuv_seq | input_sel |
+		     acq_prop | sink_fmt->yuv_seq |
 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 32/55] media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single variable
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The rkisp1_config_isp() function stores the value of the input selection
and polarity configuration in two different local variables, OR'ed
together when writing the register. Merge them into a single acq_prop
variable.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../media/platform/rockchip/rkisp1/rkisp1-isp.c  | 16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index f5b8a2e31936..4496af991c82 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
@@ -188,17 +188,17 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	/* Set up input acquisition properties */
 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
-			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
 
 		switch (sink_fmt->bus_width) {
 		case 8:
-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
 			break;
 		case 10:
-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
 			break;
 		case 12:
-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
 			break;
 		default:
 			dev_err(rkisp1->dev, "Invalid bus width\n");
@@ -208,15 +208,15 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 
 	if (mbus_type == V4L2_MBUS_PARALLEL) {
 		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
-			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
 
 		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
-			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
 	}
 
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
-		     signal | sink_fmt->yuv_seq | input_sel |
+		     acq_prop | sink_fmt->yuv_seq |
 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 33/55] media: rkisp1: isp: Initialize some variables at declaration time
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Intialize the src_fmt and sink_fmt variable when declaring them in
rkisp1_config_isp().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 4496af991c82..bf44f10200f5 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -142,12 +142,11 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
-	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
+	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
 
-	sink_fmt = isp->sink_fmt;
-	src_fmt = isp->src_fmt;
 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
 					  V4L2_SUBDEV_FORMAT_ACTIVE);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 33/55] media: rkisp1: isp: Initialize some variables at declaration time
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Intialize the src_fmt and sink_fmt variable when declaring them in
rkisp1_config_isp().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 4496af991c82..bf44f10200f5 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -142,12 +142,11 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
-	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
+	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
 	struct v4l2_mbus_framefmt *sink_frm;
 	struct v4l2_rect *sink_crop;
 
-	sink_fmt = isp->sink_fmt;
-	src_fmt = isp->src_fmt;
 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
 					  V4L2_SUBDEV_FORMAT_ACTIVE);
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 34/55] media: rkisp1: isp: Fix whitespace issues
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Add missing blank lines after variable declaration blocks, and fix
indentation issues.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 8 +++++---
 1 file changed, 5 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index bf44f10200f5..86d496855374 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -79,7 +79,8 @@ rkisp1_isp_get_pad_fmt(struct rkisp1_isp *isp,
 {
 	struct v4l2_subdev_state state = {
 		.pads = isp->pad_cfg
-		};
+	};
+
 	if (which == V4L2_SUBDEV_FORMAT_TRY)
 		return v4l2_subdev_get_try_format(&isp->sd, sd_state, pad);
 	else
@@ -93,7 +94,8 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
 {
 	struct v4l2_subdev_state state = {
 		.pads = isp->pad_cfg
-		};
+	};
+
 	if (which == V4L2_SUBDEV_FORMAT_TRY)
 		return v4l2_subdev_get_try_crop(&isp->sd, sd_state, pad);
 	else
@@ -893,8 +895,8 @@ static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
 	struct v4l2_event event = {
 		.type = V4L2_EVENT_FRAME_SYNC,
 	};
-	event.u.frame_sync.frame_sequence = isp->frame_sequence;
 
+	event.u.frame_sync.frame_sequence = isp->frame_sequence;
 	v4l2_event_queue(isp->sd.devnode, &event);
 }
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 34/55] media: rkisp1: isp: Fix whitespace issues
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Add missing blank lines after variable declaration blocks, and fix
indentation issues.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 8 +++++---
 1 file changed, 5 insertions(+), 3 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index bf44f10200f5..86d496855374 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -79,7 +79,8 @@ rkisp1_isp_get_pad_fmt(struct rkisp1_isp *isp,
 {
 	struct v4l2_subdev_state state = {
 		.pads = isp->pad_cfg
-		};
+	};
+
 	if (which == V4L2_SUBDEV_FORMAT_TRY)
 		return v4l2_subdev_get_try_format(&isp->sd, sd_state, pad);
 	else
@@ -93,7 +94,8 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
 {
 	struct v4l2_subdev_state state = {
 		.pads = isp->pad_cfg
-		};
+	};
+
 	if (which == V4L2_SUBDEV_FORMAT_TRY)
 		return v4l2_subdev_get_try_crop(&isp->sd, sd_state, pad);
 	else
@@ -893,8 +895,8 @@ static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
 	struct v4l2_event event = {
 		.type = V4L2_EVENT_FRAME_SYNC,
 	};
-	event.u.frame_sync.frame_sequence = isp->frame_sequence;
 
+	event.u.frame_sync.frame_sequence = isp->frame_sequence;
 	v4l2_event_queue(isp->sd.devnode, &event);
 }
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 35/55] media: rkisp1: isp: Constify various local variables
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

A set of local variables point to structure that are not meant to be
modified. Constify them.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 86d496855374..91b37f2dca91 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -113,7 +113,7 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
  */
 static void rkisp1_config_ism(struct rkisp1_isp *isp)
 {
-	struct v4l2_rect *src_crop =
+	const struct v4l2_rect *src_crop =
 		rkisp1_isp_get_pad_crop(isp, NULL,
 					RKISP1_ISP_PAD_SOURCE_VIDEO,
 					V4L2_SUBDEV_FORMAT_ACTIVE);
@@ -146,8 +146,8 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
 	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
 	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
-	struct v4l2_mbus_framefmt *sink_frm;
-	struct v4l2_rect *sink_crop;
+	const struct v4l2_mbus_framefmt *sink_frm;
+	const struct v4l2_rect *sink_crop;
 
 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
@@ -557,7 +557,7 @@ static void rkisp1_isp_set_sink_crop(struct rkisp1_isp *isp,
 				     struct v4l2_rect *r, unsigned int which)
 {
 	struct v4l2_rect *sink_crop, *src_crop;
-	struct v4l2_mbus_framefmt *sink_fmt;
+	const struct v4l2_mbus_framefmt *sink_fmt;
 
 	sink_crop = rkisp1_isp_get_pad_crop(isp, sd_state,
 					    RKISP1_ISP_PAD_SINK_VIDEO,
@@ -742,7 +742,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	struct rkisp1_sensor_async *asd;
+	const struct rkisp1_sensor_async *asd;
 	int ret;
 
 	if (!enable) {
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 35/55] media: rkisp1: isp: Constify various local variables
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

A set of local variables point to structure that are not meant to be
modified. Constify them.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 86d496855374..91b37f2dca91 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -113,7 +113,7 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
  */
 static void rkisp1_config_ism(struct rkisp1_isp *isp)
 {
-	struct v4l2_rect *src_crop =
+	const struct v4l2_rect *src_crop =
 		rkisp1_isp_get_pad_crop(isp, NULL,
 					RKISP1_ISP_PAD_SOURCE_VIDEO,
 					V4L2_SUBDEV_FORMAT_ACTIVE);
@@ -146,8 +146,8 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
 	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
 	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
-	struct v4l2_mbus_framefmt *sink_frm;
-	struct v4l2_rect *sink_crop;
+	const struct v4l2_mbus_framefmt *sink_frm;
+	const struct v4l2_rect *sink_crop;
 
 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
 					  RKISP1_ISP_PAD_SINK_VIDEO,
@@ -557,7 +557,7 @@ static void rkisp1_isp_set_sink_crop(struct rkisp1_isp *isp,
 				     struct v4l2_rect *r, unsigned int which)
 {
 	struct v4l2_rect *sink_crop, *src_crop;
-	struct v4l2_mbus_framefmt *sink_fmt;
+	const struct v4l2_mbus_framefmt *sink_fmt;
 
 	sink_crop = rkisp1_isp_get_pad_crop(isp, sd_state,
 					    RKISP1_ISP_PAD_SINK_VIDEO,
@@ -742,7 +742,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	struct rkisp1_sensor_async *asd;
+	const struct rkisp1_sensor_async *asd;
 	int ret;
 
 	if (!enable) {
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 36/55] media: rkisp1: isp: Rename rkisp1_get_remote_source()
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Rename the rkisp1_get_remote_source() function to
rkisp1_isp_get_source() to use a consistent rkisp1_isp_* prefix for all
ISP functions, and drop the "remote" as the source can't be local.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 91b37f2dca91..627b1ad3bf26 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -58,7 +58,7 @@
  * Helpers
  */
 
-static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
+static struct v4l2_subdev *rkisp1_isp_get_source(struct v4l2_subdev *sd)
 {
 	struct media_pad *local, *remote;
 	struct media_entity *sensor_me;
@@ -754,7 +754,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return 0;
 	}
 
-	rkisp1->source = rkisp1_get_remote_source(sd);
+	rkisp1->source = rkisp1_isp_get_source(sd);
 	if (!rkisp1->source) {
 		dev_warn(rkisp1->dev, "No link between isp and source\n");
 		return -ENODEV;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 36/55] media: rkisp1: isp: Rename rkisp1_get_remote_source()
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Rename the rkisp1_get_remote_source() function to
rkisp1_isp_get_source() to use a consistent rkisp1_isp_* prefix for all
ISP functions, and drop the "remote" as the source can't be local.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 91b37f2dca91..627b1ad3bf26 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -58,7 +58,7 @@
  * Helpers
  */
 
-static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
+static struct v4l2_subdev *rkisp1_isp_get_source(struct v4l2_subdev *sd)
 {
 	struct media_pad *local, *remote;
 	struct media_entity *sensor_me;
@@ -754,7 +754,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return 0;
 	}
 
-	rkisp1->source = rkisp1_get_remote_source(sd);
+	rkisp1->source = rkisp1_isp_get_source(sd);
 	if (!rkisp1->source) {
 		dev_warn(rkisp1->dev, "No link between isp and source\n");
 		return -ENODEV;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The media_entity_remote_pad() helper function returns the first remote
pad it find connected to a given pad. Beside being possibly ill-named
(as it operates on a pad, not an entity) and non-deterministic (as it
stops at the first enabled link), the fact that it returns the first
match makes it unsuitable for drivers that need to guarantee that a
single link is enabled, for instance when an entity can process data
from one of multiple sources at a time.

For those use cases, add a new helper function,
media_entity_remote_pad_unique(), that operates on an entity and returns
a remote pad, with a guarantee that only one link is enabled. To ease
its use in drivers, also add an inline wrapper that locates source pads
specifically. A wrapper that locates sink pads can easily be added when
needed.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 Documentation/driver-api/media/mc-core.rst |  4 +-
 drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
 include/media/media-entity.h               | 45 ++++++++++++++++++++++
 3 files changed, 85 insertions(+), 2 deletions(-)

diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
index 02481a2513b9..a2d1e32e3abb 100644
--- a/Documentation/driver-api/media/mc-core.rst
+++ b/Documentation/driver-api/media/mc-core.rst
@@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
 
 Helper functions can be used to find a link between two given pads, or a pad
 connected to another pad through an enabled link
-:c:func:`media_entity_find_link()` and
-:c:func:`media_entity_remote_pad()`.
+(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
+:c:func:`media_entity_remote_source_pad()`).
 
 Use count and power handling
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
index 11f5207f73aa..1febf5a86be6 100644
--- a/drivers/media/mc/mc-entity.c
+++ b/drivers/media/mc/mc-entity.c
@@ -9,6 +9,7 @@
  */
 
 #include <linux/bitmap.h>
+#include <linux/list.h>
 #include <linux/property.h>
 #include <linux/slab.h>
 #include <media/media-entity.h>
@@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
 }
 EXPORT_SYMBOL_GPL(media_entity_remote_pad);
 
+struct media_pad *
+media_entity_remote_pad_unique(const struct media_entity *entity,
+			       unsigned int type)
+{
+	struct media_pad *pad = NULL;
+	struct media_link *link;
+
+	list_for_each_entry(link, &entity->links, list) {
+		struct media_pad *local_pad;
+		struct media_pad *remote_pad;
+
+		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
+			continue;
+
+		if (type == MEDIA_PAD_FL_SOURCE) {
+			local_pad = link->sink;
+			remote_pad = link->source;
+		} else {
+			local_pad = link->source;
+			remote_pad = link->sink;
+		}
+
+		if (local_pad->entity == entity) {
+			if (pad)
+				return ERR_PTR(-ENOTUNIQ);
+
+			pad = remote_pad;
+		}
+	}
+
+	if (!pad)
+		return ERR_PTR(-ENOLINK);
+
+	return pad;
+}
+EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
+
 static void media_interface_init(struct media_device *mdev,
 				 struct media_interface *intf,
 				 u32 gobj_type,
diff --git a/include/media/media-entity.h b/include/media/media-entity.h
index a9a1c0ec5d1c..33d5f52719a0 100644
--- a/include/media/media-entity.h
+++ b/include/media/media-entity.h
@@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
  */
 struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
 
+/**
+ * media_entity_remote_pad_unique - Find a remote pad connected to an entity
+ * @entity: The entity
+ * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
+ *
+ * Search for and return a remote pad of @type connected to @entity through an
+ * enabled link. If multiple (or no) remote pads match these criteria, an error
+ * is returned.
+ *
+ * The uniqueness constraint makes this helper function suitable for entities
+ * that support a single active source or sink at a time.
+ *
+ * Return: A pointer to the remote pad, or one of the following error pointers
+ * if an error occurs:
+ *
+ * * -ENOTUNIQ - Multiple links are enabled
+ * * -ENOLINK - No connected pad found
+ */
+struct media_pad *
+media_entity_remote_pad_unique(const struct media_entity *entity,
+			       unsigned int type);
+
+/**
+ * media_entity_remote_source_pad - Find a remote source pad connected to an entity
+ * @entity: The entity
+ *
+ * Search for and return a remote source pad connected to @entity through an
+ * enabled link. If multiple (or no) remote pads match these criteria, an error
+ * is returned.
+ *
+ * The uniqueness constraint makes this helper function suitable for entities
+ * that support a single active source at a time.
+ *
+ * Return: A pointer to the remote pad, or one of the following error pointers
+ * if an error occurs:
+ *
+ * * -ENOTUNIQ - Multiple links are enabled
+ * * -ENOLINK - No connected pad found
+ */
+static inline struct media_pad *
+media_entity_remote_source_pad(const struct media_entity *entity)
+{
+	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
+}
+
 /**
  * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
  * @entity: The entity
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The media_entity_remote_pad() helper function returns the first remote
pad it find connected to a given pad. Beside being possibly ill-named
(as it operates on a pad, not an entity) and non-deterministic (as it
stops at the first enabled link), the fact that it returns the first
match makes it unsuitable for drivers that need to guarantee that a
single link is enabled, for instance when an entity can process data
from one of multiple sources at a time.

For those use cases, add a new helper function,
media_entity_remote_pad_unique(), that operates on an entity and returns
a remote pad, with a guarantee that only one link is enabled. To ease
its use in drivers, also add an inline wrapper that locates source pads
specifically. A wrapper that locates sink pads can easily be added when
needed.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 Documentation/driver-api/media/mc-core.rst |  4 +-
 drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
 include/media/media-entity.h               | 45 ++++++++++++++++++++++
 3 files changed, 85 insertions(+), 2 deletions(-)

diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
index 02481a2513b9..a2d1e32e3abb 100644
--- a/Documentation/driver-api/media/mc-core.rst
+++ b/Documentation/driver-api/media/mc-core.rst
@@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
 
 Helper functions can be used to find a link between two given pads, or a pad
 connected to another pad through an enabled link
-:c:func:`media_entity_find_link()` and
-:c:func:`media_entity_remote_pad()`.
+(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
+:c:func:`media_entity_remote_source_pad()`).
 
 Use count and power handling
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
index 11f5207f73aa..1febf5a86be6 100644
--- a/drivers/media/mc/mc-entity.c
+++ b/drivers/media/mc/mc-entity.c
@@ -9,6 +9,7 @@
  */
 
 #include <linux/bitmap.h>
+#include <linux/list.h>
 #include <linux/property.h>
 #include <linux/slab.h>
 #include <media/media-entity.h>
@@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
 }
 EXPORT_SYMBOL_GPL(media_entity_remote_pad);
 
+struct media_pad *
+media_entity_remote_pad_unique(const struct media_entity *entity,
+			       unsigned int type)
+{
+	struct media_pad *pad = NULL;
+	struct media_link *link;
+
+	list_for_each_entry(link, &entity->links, list) {
+		struct media_pad *local_pad;
+		struct media_pad *remote_pad;
+
+		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
+			continue;
+
+		if (type == MEDIA_PAD_FL_SOURCE) {
+			local_pad = link->sink;
+			remote_pad = link->source;
+		} else {
+			local_pad = link->source;
+			remote_pad = link->sink;
+		}
+
+		if (local_pad->entity == entity) {
+			if (pad)
+				return ERR_PTR(-ENOTUNIQ);
+
+			pad = remote_pad;
+		}
+	}
+
+	if (!pad)
+		return ERR_PTR(-ENOLINK);
+
+	return pad;
+}
+EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
+
 static void media_interface_init(struct media_device *mdev,
 				 struct media_interface *intf,
 				 u32 gobj_type,
diff --git a/include/media/media-entity.h b/include/media/media-entity.h
index a9a1c0ec5d1c..33d5f52719a0 100644
--- a/include/media/media-entity.h
+++ b/include/media/media-entity.h
@@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
  */
 struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
 
+/**
+ * media_entity_remote_pad_unique - Find a remote pad connected to an entity
+ * @entity: The entity
+ * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
+ *
+ * Search for and return a remote pad of @type connected to @entity through an
+ * enabled link. If multiple (or no) remote pads match these criteria, an error
+ * is returned.
+ *
+ * The uniqueness constraint makes this helper function suitable for entities
+ * that support a single active source or sink at a time.
+ *
+ * Return: A pointer to the remote pad, or one of the following error pointers
+ * if an error occurs:
+ *
+ * * -ENOTUNIQ - Multiple links are enabled
+ * * -ENOLINK - No connected pad found
+ */
+struct media_pad *
+media_entity_remote_pad_unique(const struct media_entity *entity,
+			       unsigned int type);
+
+/**
+ * media_entity_remote_source_pad - Find a remote source pad connected to an entity
+ * @entity: The entity
+ *
+ * Search for and return a remote source pad connected to @entity through an
+ * enabled link. If multiple (or no) remote pads match these criteria, an error
+ * is returned.
+ *
+ * The uniqueness constraint makes this helper function suitable for entities
+ * that support a single active source at a time.
+ *
+ * Return: A pointer to the remote pad, or one of the following error pointers
+ * if an error occurs:
+ *
+ * * -ENOTUNIQ - Multiple links are enabled
+ * * -ENOLINK - No connected pad found
+ */
+static inline struct media_pad *
+media_entity_remote_source_pad(const struct media_entity *entity)
+{
+	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
+}
+
 /**
  * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
  * @entity: The entity
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The newly added media_entity_remote_source_pad() helper function handles
use cases where the entity has a link enabled uniqueness constraint
covering all pads. There are use cases where the constraint covers a
specific pad only. Add a new media_pad_remote_pad() function to handle
this. It operates as media_entity_remote_source_pad(), but on a given
pad instead of on the entity.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 Documentation/driver-api/media/mc-core.rst |  4 +--
 drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
 include/media/media-entity.h               | 18 +++++++++++++
 3 files changed, 51 insertions(+), 2 deletions(-)

diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
index a2d1e32e3abb..83c3bdbf67be 100644
--- a/Documentation/driver-api/media/mc-core.rst
+++ b/Documentation/driver-api/media/mc-core.rst
@@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
 
 Helper functions can be used to find a link between two given pads, or a pad
 connected to another pad through an enabled link
-(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
-:c:func:`media_entity_remote_source_pad()`).
+(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
+:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
 
 Use count and power handling
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
index 1febf5a86be6..6429b0510bfb 100644
--- a/drivers/media/mc/mc-entity.c
+++ b/drivers/media/mc/mc-entity.c
@@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
 }
 EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
 
+struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
+{
+	struct media_pad *found_pad = NULL;
+	struct media_link *link;
+
+	list_for_each_entry(link, &pad->entity->links, list) {
+		struct media_pad *remote_pad;
+
+		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
+			continue;
+
+		if (link->sink == pad)
+			remote_pad = link->source;
+		else if (link->source == pad)
+			remote_pad = link->sink;
+		else
+			continue;
+
+		if (found_pad)
+			return ERR_PTR(-ENOTUNIQ);
+
+		found_pad = remote_pad;
+	}
+
+	if (!found_pad)
+		return ERR_PTR(-ENOLINK);
+
+	return found_pad;
+}
+EXPORT_SYMBOL_GPL(media_pad_remote_pad);
+
 static void media_interface_init(struct media_device *mdev,
 				 struct media_interface *intf,
 				 u32 gobj_type,
diff --git a/include/media/media-entity.h b/include/media/media-entity.h
index 33d5f52719a0..bfe6a7b10a68 100644
--- a/include/media/media-entity.h
+++ b/include/media/media-entity.h
@@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
 	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
 }
 
+/**
+ * media_pad_remote_pad - Find a remote pad connected to a pad
+ * @pad: The pad
+ *
+ * Search for and return a remote pad connected to @pad through an enabled
+ * link. If multiple (or no) remote pads are found, an error is returned.
+ *
+ * The uniqueness constraint makes this helper function suitable for entities
+ * that support a single active source at a time on a given pad.
+ *
+ * Return: A pointer to the remote pad, or one of the following error pointers
+ * if an error occurs:
+ *
+ * * -ENOTUNIQ - Multiple links are enabled
+ * * -ENOLINK - No connected pad found
+ */
+struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
+
 /**
  * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
  * @entity: The entity
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The newly added media_entity_remote_source_pad() helper function handles
use cases where the entity has a link enabled uniqueness constraint
covering all pads. There are use cases where the constraint covers a
specific pad only. Add a new media_pad_remote_pad() function to handle
this. It operates as media_entity_remote_source_pad(), but on a given
pad instead of on the entity.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 Documentation/driver-api/media/mc-core.rst |  4 +--
 drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
 include/media/media-entity.h               | 18 +++++++++++++
 3 files changed, 51 insertions(+), 2 deletions(-)

diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
index a2d1e32e3abb..83c3bdbf67be 100644
--- a/Documentation/driver-api/media/mc-core.rst
+++ b/Documentation/driver-api/media/mc-core.rst
@@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
 
 Helper functions can be used to find a link between two given pads, or a pad
 connected to another pad through an enabled link
-(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
-:c:func:`media_entity_remote_source_pad()`).
+(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
+:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
 
 Use count and power handling
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
index 1febf5a86be6..6429b0510bfb 100644
--- a/drivers/media/mc/mc-entity.c
+++ b/drivers/media/mc/mc-entity.c
@@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
 }
 EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
 
+struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
+{
+	struct media_pad *found_pad = NULL;
+	struct media_link *link;
+
+	list_for_each_entry(link, &pad->entity->links, list) {
+		struct media_pad *remote_pad;
+
+		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
+			continue;
+
+		if (link->sink == pad)
+			remote_pad = link->source;
+		else if (link->source == pad)
+			remote_pad = link->sink;
+		else
+			continue;
+
+		if (found_pad)
+			return ERR_PTR(-ENOTUNIQ);
+
+		found_pad = remote_pad;
+	}
+
+	if (!found_pad)
+		return ERR_PTR(-ENOLINK);
+
+	return found_pad;
+}
+EXPORT_SYMBOL_GPL(media_pad_remote_pad);
+
 static void media_interface_init(struct media_device *mdev,
 				 struct media_interface *intf,
 				 u32 gobj_type,
diff --git a/include/media/media-entity.h b/include/media/media-entity.h
index 33d5f52719a0..bfe6a7b10a68 100644
--- a/include/media/media-entity.h
+++ b/include/media/media-entity.h
@@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
 	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
 }
 
+/**
+ * media_pad_remote_pad - Find a remote pad connected to a pad
+ * @pad: The pad
+ *
+ * Search for and return a remote pad connected to @pad through an enabled
+ * link. If multiple (or no) remote pads are found, an error is returned.
+ *
+ * The uniqueness constraint makes this helper function suitable for entities
+ * that support a single active source at a time on a given pad.
+ *
+ * Return: A pointer to the remote pad, or one of the following error pointers
+ * if an error occurs:
+ *
+ * * -ENOTUNIQ - Multiple links are enabled
+ * * -ENOLINK - No connected pad found
+ */
+struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
+
 /**
  * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
  * @entity: The entity
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 39/55] media: rkisp1: isp: Disallow multiple active sources
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP supports multiple source subdevs, but can only capture from a
single one at a time. The source is selected through link setup. The
driver finds the active source in its .s_stream() handler using the
media_entity_remote_pad() function. This fails to reject invalid
configurations with multiple active sources. Fix it by using the
media_entity_remote_source_pad() helper instead, and inline
rkisp1_isp_get_source() in rkisp1_isp_s_stream() as the function is
small and has a single caller.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 28 ++++++++-----------
 1 file changed, 11 insertions(+), 17 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 627b1ad3bf26..5afb8be311c7 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -58,20 +58,6 @@
  * Helpers
  */
 
-static struct v4l2_subdev *rkisp1_isp_get_source(struct v4l2_subdev *sd)
-{
-	struct media_pad *local, *remote;
-	struct media_entity *sensor_me;
-
-	local = &sd->entity.pads[RKISP1_ISP_PAD_SINK_VIDEO];
-	remote = media_entity_remote_pad(local);
-	if (!remote)
-		return NULL;
-
-	sensor_me = remote->entity;
-	return media_entity_to_v4l2_subdev(sensor_me);
-}
-
 static struct v4l2_mbus_framefmt *
 rkisp1_isp_get_pad_fmt(struct rkisp1_isp *isp,
 		       struct v4l2_subdev_state *sd_state,
@@ -743,6 +729,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	const struct rkisp1_sensor_async *asd;
+	struct media_pad *source_pad;
 	int ret;
 
 	if (!enable) {
@@ -754,10 +741,17 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return 0;
 	}
 
-	rkisp1->source = rkisp1_isp_get_source(sd);
+	source_pad = media_pad_remote_pad(&isp->pads[RKISP1_ISP_PAD_SINK_VIDEO]);
+	if (IS_ERR(source_pad)) {
+		dev_dbg(rkisp1->dev, "Failed to get source for ISP: %ld\n",
+			PTR_ERR(source_pad));
+		return -EPIPE;
+	}
+
+	rkisp1->source = media_entity_to_v4l2_subdev(source_pad->entity);
 	if (!rkisp1->source) {
-		dev_warn(rkisp1->dev, "No link between isp and source\n");
-		return -ENODEV;
+		/* This should really not happen, so is not worth a message. */
+		return -EPIPE;
 	}
 
 	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 39/55] media: rkisp1: isp: Disallow multiple active sources
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The ISP supports multiple source subdevs, but can only capture from a
single one at a time. The source is selected through link setup. The
driver finds the active source in its .s_stream() handler using the
media_entity_remote_pad() function. This fails to reject invalid
configurations with multiple active sources. Fix it by using the
media_entity_remote_source_pad() helper instead, and inline
rkisp1_isp_get_source() in rkisp1_isp_s_stream() as the function is
small and has a single caller.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 28 ++++++++-----------
 1 file changed, 11 insertions(+), 17 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 627b1ad3bf26..5afb8be311c7 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -58,20 +58,6 @@
  * Helpers
  */
 
-static struct v4l2_subdev *rkisp1_isp_get_source(struct v4l2_subdev *sd)
-{
-	struct media_pad *local, *remote;
-	struct media_entity *sensor_me;
-
-	local = &sd->entity.pads[RKISP1_ISP_PAD_SINK_VIDEO];
-	remote = media_entity_remote_pad(local);
-	if (!remote)
-		return NULL;
-
-	sensor_me = remote->entity;
-	return media_entity_to_v4l2_subdev(sensor_me);
-}
-
 static struct v4l2_mbus_framefmt *
 rkisp1_isp_get_pad_fmt(struct rkisp1_isp *isp,
 		       struct v4l2_subdev_state *sd_state,
@@ -743,6 +729,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	const struct rkisp1_sensor_async *asd;
+	struct media_pad *source_pad;
 	int ret;
 
 	if (!enable) {
@@ -754,10 +741,17 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return 0;
 	}
 
-	rkisp1->source = rkisp1_isp_get_source(sd);
+	source_pad = media_pad_remote_pad(&isp->pads[RKISP1_ISP_PAD_SINK_VIDEO]);
+	if (IS_ERR(source_pad)) {
+		dev_dbg(rkisp1->dev, "Failed to get source for ISP: %ld\n",
+			PTR_ERR(source_pad));
+		return -EPIPE;
+	}
+
+	rkisp1->source = media_entity_to_v4l2_subdev(source_pad->entity);
 	if (!rkisp1->source) {
-		dev_warn(rkisp1->dev, "No link between isp and source\n");
-		return -ENODEV;
+		/* This should really not happen, so is not worth a message. */
+		return -EPIPE;
 	}
 
 	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The CSI receiver is a component separate from the ISP or the resizers.
It is actually optional, not all device model include a CSI receiver. On
some SoCs CSI-2 support can be provided through an external CSI-2
receiver, connected to the ISP's parallel input.

To support those use cases, create a V4L2 subdev to model the CSI
receiver. It will allow the driver to handle both internal and external
CSI receivers the same way.

The next commit will plumb the CSI subdev to the rest of the driver,
replacing direct function calls.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
 4 files changed, 313 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 3c55e922346e..0ab49d1feb55 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
 	RKISP1_RSZ_PAD_MAX
 };
 
+/* enum for the csi receiver pads */
+enum rkisp1_csi_pad {
+	RKISP1_CSI_PAD_SINK,
+	RKISP1_CSI_PAD_SRC,
+	RKISP1_CSI_PAD_MAX
+};
+
 /* enum for the capture id */
 enum rkisp1_stream_id {
 	RKISP1_MAINPATH,
@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
  * @rkisp1: pointer to the rkisp1 device
  * @dphy: a pointer to the phy
  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
+ * @sd: v4l2_subdev variable
+ * @pads: media pads
+ * @pad_cfg: configurations for the pads
+ * @ops_lock: a lock for the subdev ops
+ * @source: source in-use, set when starting streaming
  */
 struct rkisp1_csi {
 	struct rkisp1_device *rkisp1;
 	struct phy *dphy;
 	bool is_dphy_errctrl_disabled;
+	struct v4l2_subdev sd;
+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
+	struct mutex ops_lock; /* serialize the subdevice ops */
+	struct rkisp1_sensor_async *source;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 425a3b014089..8182694a6fe0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -15,10 +15,34 @@
 #include <linux/phy/phy-mipi-dphy.h>
 
 #include <media/v4l2-ctrls.h>
+#include <media/v4l2-fwnode.h>
 
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
+
+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
+
+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
+{
+	return container_of(sd, struct rkisp1_csi, sd);
+}
+
+static struct v4l2_mbus_framefmt *
+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
+		       struct v4l2_subdev_state *sd_state,
+		       unsigned int pad, u32 which)
+{
+	struct v4l2_subdev_state state = {
+		.pads = csi->pad_cfg
+	};
+	if (which == V4L2_SUBDEV_FORMAT_TRY)
+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
+	else
+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
+}
+
 static int rkisp1_csi_config(struct rkisp1_csi *csi,
 			     const struct rkisp1_sensor_async *sensor)
 {
@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
 	return IRQ_HANDLED;
 }
 
+/* ----------------------------------------------------------------------------
+ * Subdev pad operations
+ */
+
+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
+				   struct v4l2_subdev_state *sd_state,
+				   struct v4l2_mbus_framefmt *format,
+				   unsigned int which)
+{
+	struct v4l2_mbus_framefmt *sink_fmt;
+
+	/* We don't set the src format directly; take it from the sink format */
+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
+					  which);
+
+	*format = *sink_fmt;
+}
+
+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
+				    struct v4l2_subdev_state *sd_state,
+				    struct v4l2_mbus_framefmt *format,
+				    unsigned int which)
+{
+	const struct rkisp1_mbus_info *mbus_info;
+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
+
+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
+					  which);
+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
+					 which);
+
+	sink_fmt->code = format->code;
+
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
+	}
+
+	sink_fmt->width = clamp_t(u32, format->width,
+				  RKISP1_ISP_MIN_WIDTH,
+				  RKISP1_ISP_MAX_WIDTH);
+	sink_fmt->height = clamp_t(u32, format->height,
+				   RKISP1_ISP_MIN_HEIGHT,
+				   RKISP1_ISP_MAX_HEIGHT);
+
+	/* Propagate to source pad */
+	src_fmt->code = sink_fmt->code;
+	src_fmt->width = sink_fmt->width;
+	src_fmt->height = sink_fmt->height;
+
+	*format = *sink_fmt;
+}
+
+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
+				     struct v4l2_subdev_state *sd_state,
+				     struct v4l2_subdev_mbus_code_enum *code)
+{
+	unsigned int i;
+	int pos = 0;
+
+	if (code->index >= rkisp1_mbus_info_length())
+		return -EINVAL;
+
+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
+		const struct rkisp1_mbus_info *fmt =
+			rkisp1_mbus_info_get_by_index(i);
+
+		if (fmt->direction & RKISP1_ISP_SD_SINK)
+			pos++;
+
+		if (code->index == pos - 1) {
+			code->code = fmt->mbus_code;
+			return 0;
+		}
+	}
+
+	return -EINVAL;
+}
+
+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
+				  struct v4l2_subdev_state *sd_state)
+{
+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
+
+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
+					      RKISP1_CSI_PAD_SRC);
+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
+	sink_fmt->field = V4L2_FIELD_NONE;
+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
+
+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
+					     RKISP1_CSI_PAD_SINK);
+	*src_fmt = *sink_fmt;
+
+	return 0;
+}
+
+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
+			      struct v4l2_subdev_state *sd_state,
+			      struct v4l2_subdev_format *fmt)
+{
+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
+
+	mutex_lock(&csi->ops_lock);
+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
+					      fmt->which);
+	mutex_unlock(&csi->ops_lock);
+	return 0;
+}
+
+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
+			      struct v4l2_subdev_state *sd_state,
+			      struct v4l2_subdev_format *fmt)
+{
+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
+
+	mutex_lock(&csi->ops_lock);
+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
+					fmt->which);
+	else
+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
+				       fmt->which);
+
+	mutex_unlock(&csi->ops_lock);
+	return 0;
+}
+
+/* ----------------------------------------------------------------------------
+ * Subdev video operations
+ */
+
+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
+{
+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	struct media_pad *source_pad;
+	struct v4l2_subdev *source;
+	int ret;
+
+	if (!enable) {
+		v4l2_subdev_call(csi->source->sd, video, s_stream,
+				 false);
+
+		rkisp1_csi_stop(csi);
+
+		return ret;
+	}
+
+	source_pad = media_entity_remote_source_pad(&sd->entity);
+	if (IS_ERR(source_pad)) {
+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);
+		return -EPIPE;
+	}
+
+	source = media_entity_to_v4l2_subdev(source_pad->entity);
+	if (!source) {
+		/* This should really not happen, so is not worth a message. */
+		return -EPIPE;
+	}
+
+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
+				   asd);
+
+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
+		return -EINVAL;
+
+	mutex_lock(&csi->ops_lock);
+	ret = rkisp1_csi_start(csi, csi->source);
+	mutex_unlock(&csi->ops_lock);
+	if (ret)
+		return ret;
+
+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
+
+	return 0;
+}
+
+/* ----------------------------------------------------------------------------
+ * Registration
+ */
+
+static const struct media_entity_operations rkisp1_csi_media_ops = {
+	.link_validate = v4l2_subdev_link_validate,
+};
+
+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
+	.s_stream = rkisp1_csi_s_stream,
+};
+
+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
+	.init_cfg = rkisp1_csi_init_config,
+	.get_fmt = rkisp1_csi_get_fmt,
+	.set_fmt = rkisp1_csi_set_fmt,
+};
+
+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
+	.video = &rkisp1_csi_video_ops,
+	.pad = &rkisp1_csi_pad_ops,
+};
+
+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+	struct v4l2_subdev_state state = {};
+	struct media_pad *pads;
+	struct v4l2_subdev *sd;
+	int ret;
+
+	csi->rkisp1 = rkisp1;
+	mutex_init(&csi->ops_lock);
+
+	sd = &csi->sd;
+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
+	sd->entity.ops = &rkisp1_csi_media_ops;
+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
+	sd->owner = THIS_MODULE;
+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
+
+	pads = csi->pads;
+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
+					  MEDIA_PAD_FL_MUST_CONNECT;
+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
+					 MEDIA_PAD_FL_MUST_CONNECT;
+
+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
+	if (ret)
+		goto error;
+
+	state.pads = csi->pad_cfg;
+	rkisp1_csi_init_config(sd, &state);
+
+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
+	if (ret) {
+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
+		goto error;
+	}
+
+	return 0;
+
+error:
+	media_entity_cleanup(&sd->entity);
+	mutex_destroy(&csi->ops_lock);
+	csi->rkisp1 = NULL;
+	return ret;
+}
+
+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+
+	if (!csi->rkisp1)
+		return;
+
+	v4l2_device_unregister_subdev(&csi->sd);
+	media_entity_cleanup(&csi->sd.entity);
+	mutex_destroy(&csi->ops_lock);
+}
+
 int rkisp1_csi_init(struct rkisp1_device *rkisp1)
 {
 	struct rkisp1_csi *csi = &rkisp1->csi;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index 97ce7e7959ab..ddf8e5e08f55 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -13,10 +13,14 @@
 
 struct rkisp1_device;
 struct rkisp1_sensor_async;
+struct v4l2_subdev;
 
 int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
+
 int rkisp1_csi_start(struct rkisp1_csi *csi,
 		     const struct rkisp1_sensor_async *sensor);
 void rkisp1_csi_stop(struct rkisp1_csi *csi);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 253220188abd..faf2cd4c8149 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 
 static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
 {
+	rkisp1_csi_unregister(rkisp1);
 	rkisp1_params_unregister(rkisp1);
 	rkisp1_stats_unregister(rkisp1);
 	rkisp1_capture_devs_unregister(rkisp1);
@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
+	ret = rkisp1_csi_register(rkisp1);
+	if (ret)
+		goto error;
+
 	ret = rkisp1_create_links(rkisp1);
 	if (ret)
 		goto error;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The CSI receiver is a component separate from the ISP or the resizers.
It is actually optional, not all device model include a CSI receiver. On
some SoCs CSI-2 support can be provided through an external CSI-2
receiver, connected to the ISP's parallel input.

To support those use cases, create a V4L2 subdev to model the CSI
receiver. It will allow the driver to handle both internal and external
CSI receivers the same way.

The next commit will plumb the CSI subdev to the rest of the driver,
replacing direct function calls.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
 4 files changed, 313 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 3c55e922346e..0ab49d1feb55 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
 	RKISP1_RSZ_PAD_MAX
 };
 
+/* enum for the csi receiver pads */
+enum rkisp1_csi_pad {
+	RKISP1_CSI_PAD_SINK,
+	RKISP1_CSI_PAD_SRC,
+	RKISP1_CSI_PAD_MAX
+};
+
 /* enum for the capture id */
 enum rkisp1_stream_id {
 	RKISP1_MAINPATH,
@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
  * @rkisp1: pointer to the rkisp1 device
  * @dphy: a pointer to the phy
  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
+ * @sd: v4l2_subdev variable
+ * @pads: media pads
+ * @pad_cfg: configurations for the pads
+ * @ops_lock: a lock for the subdev ops
+ * @source: source in-use, set when starting streaming
  */
 struct rkisp1_csi {
 	struct rkisp1_device *rkisp1;
 	struct phy *dphy;
 	bool is_dphy_errctrl_disabled;
+	struct v4l2_subdev sd;
+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
+	struct mutex ops_lock; /* serialize the subdevice ops */
+	struct rkisp1_sensor_async *source;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 425a3b014089..8182694a6fe0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -15,10 +15,34 @@
 #include <linux/phy/phy-mipi-dphy.h>
 
 #include <media/v4l2-ctrls.h>
+#include <media/v4l2-fwnode.h>
 
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
 
+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
+
+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
+
+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
+{
+	return container_of(sd, struct rkisp1_csi, sd);
+}
+
+static struct v4l2_mbus_framefmt *
+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
+		       struct v4l2_subdev_state *sd_state,
+		       unsigned int pad, u32 which)
+{
+	struct v4l2_subdev_state state = {
+		.pads = csi->pad_cfg
+	};
+	if (which == V4L2_SUBDEV_FORMAT_TRY)
+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
+	else
+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
+}
+
 static int rkisp1_csi_config(struct rkisp1_csi *csi,
 			     const struct rkisp1_sensor_async *sensor)
 {
@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
 	return IRQ_HANDLED;
 }
 
+/* ----------------------------------------------------------------------------
+ * Subdev pad operations
+ */
+
+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
+				   struct v4l2_subdev_state *sd_state,
+				   struct v4l2_mbus_framefmt *format,
+				   unsigned int which)
+{
+	struct v4l2_mbus_framefmt *sink_fmt;
+
+	/* We don't set the src format directly; take it from the sink format */
+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
+					  which);
+
+	*format = *sink_fmt;
+}
+
+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
+				    struct v4l2_subdev_state *sd_state,
+				    struct v4l2_mbus_framefmt *format,
+				    unsigned int which)
+{
+	const struct rkisp1_mbus_info *mbus_info;
+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
+
+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
+					  which);
+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
+					 which);
+
+	sink_fmt->code = format->code;
+
+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
+	}
+
+	sink_fmt->width = clamp_t(u32, format->width,
+				  RKISP1_ISP_MIN_WIDTH,
+				  RKISP1_ISP_MAX_WIDTH);
+	sink_fmt->height = clamp_t(u32, format->height,
+				   RKISP1_ISP_MIN_HEIGHT,
+				   RKISP1_ISP_MAX_HEIGHT);
+
+	/* Propagate to source pad */
+	src_fmt->code = sink_fmt->code;
+	src_fmt->width = sink_fmt->width;
+	src_fmt->height = sink_fmt->height;
+
+	*format = *sink_fmt;
+}
+
+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
+				     struct v4l2_subdev_state *sd_state,
+				     struct v4l2_subdev_mbus_code_enum *code)
+{
+	unsigned int i;
+	int pos = 0;
+
+	if (code->index >= rkisp1_mbus_info_length())
+		return -EINVAL;
+
+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
+		const struct rkisp1_mbus_info *fmt =
+			rkisp1_mbus_info_get_by_index(i);
+
+		if (fmt->direction & RKISP1_ISP_SD_SINK)
+			pos++;
+
+		if (code->index == pos - 1) {
+			code->code = fmt->mbus_code;
+			return 0;
+		}
+	}
+
+	return -EINVAL;
+}
+
+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
+				  struct v4l2_subdev_state *sd_state)
+{
+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
+
+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
+					      RKISP1_CSI_PAD_SRC);
+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
+	sink_fmt->field = V4L2_FIELD_NONE;
+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
+
+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
+					     RKISP1_CSI_PAD_SINK);
+	*src_fmt = *sink_fmt;
+
+	return 0;
+}
+
+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
+			      struct v4l2_subdev_state *sd_state,
+			      struct v4l2_subdev_format *fmt)
+{
+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
+
+	mutex_lock(&csi->ops_lock);
+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
+					      fmt->which);
+	mutex_unlock(&csi->ops_lock);
+	return 0;
+}
+
+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
+			      struct v4l2_subdev_state *sd_state,
+			      struct v4l2_subdev_format *fmt)
+{
+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
+
+	mutex_lock(&csi->ops_lock);
+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
+					fmt->which);
+	else
+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
+				       fmt->which);
+
+	mutex_unlock(&csi->ops_lock);
+	return 0;
+}
+
+/* ----------------------------------------------------------------------------
+ * Subdev video operations
+ */
+
+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
+{
+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
+	struct rkisp1_device *rkisp1 = csi->rkisp1;
+	struct media_pad *source_pad;
+	struct v4l2_subdev *source;
+	int ret;
+
+	if (!enable) {
+		v4l2_subdev_call(csi->source->sd, video, s_stream,
+				 false);
+
+		rkisp1_csi_stop(csi);
+
+		return ret;
+	}
+
+	source_pad = media_entity_remote_source_pad(&sd->entity);
+	if (IS_ERR(source_pad)) {
+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);
+		return -EPIPE;
+	}
+
+	source = media_entity_to_v4l2_subdev(source_pad->entity);
+	if (!source) {
+		/* This should really not happen, so is not worth a message. */
+		return -EPIPE;
+	}
+
+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
+				   asd);
+
+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
+		return -EINVAL;
+
+	mutex_lock(&csi->ops_lock);
+	ret = rkisp1_csi_start(csi, csi->source);
+	mutex_unlock(&csi->ops_lock);
+	if (ret)
+		return ret;
+
+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
+
+	return 0;
+}
+
+/* ----------------------------------------------------------------------------
+ * Registration
+ */
+
+static const struct media_entity_operations rkisp1_csi_media_ops = {
+	.link_validate = v4l2_subdev_link_validate,
+};
+
+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
+	.s_stream = rkisp1_csi_s_stream,
+};
+
+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
+	.init_cfg = rkisp1_csi_init_config,
+	.get_fmt = rkisp1_csi_get_fmt,
+	.set_fmt = rkisp1_csi_set_fmt,
+};
+
+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
+	.video = &rkisp1_csi_video_ops,
+	.pad = &rkisp1_csi_pad_ops,
+};
+
+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+	struct v4l2_subdev_state state = {};
+	struct media_pad *pads;
+	struct v4l2_subdev *sd;
+	int ret;
+
+	csi->rkisp1 = rkisp1;
+	mutex_init(&csi->ops_lock);
+
+	sd = &csi->sd;
+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
+	sd->entity.ops = &rkisp1_csi_media_ops;
+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
+	sd->owner = THIS_MODULE;
+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
+
+	pads = csi->pads;
+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
+					  MEDIA_PAD_FL_MUST_CONNECT;
+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
+					 MEDIA_PAD_FL_MUST_CONNECT;
+
+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
+	if (ret)
+		goto error;
+
+	state.pads = csi->pad_cfg;
+	rkisp1_csi_init_config(sd, &state);
+
+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
+	if (ret) {
+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
+		goto error;
+	}
+
+	return 0;
+
+error:
+	media_entity_cleanup(&sd->entity);
+	mutex_destroy(&csi->ops_lock);
+	csi->rkisp1 = NULL;
+	return ret;
+}
+
+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+
+	if (!csi->rkisp1)
+		return;
+
+	v4l2_device_unregister_subdev(&csi->sd);
+	media_entity_cleanup(&csi->sd.entity);
+	mutex_destroy(&csi->ops_lock);
+}
+
 int rkisp1_csi_init(struct rkisp1_device *rkisp1)
 {
 	struct rkisp1_csi *csi = &rkisp1->csi;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index 97ce7e7959ab..ddf8e5e08f55 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -13,10 +13,14 @@
 
 struct rkisp1_device;
 struct rkisp1_sensor_async;
+struct v4l2_subdev;
 
 int rkisp1_csi_init(struct rkisp1_device *rkisp1);
 void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 
+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
+
 int rkisp1_csi_start(struct rkisp1_csi *csi,
 		     const struct rkisp1_sensor_async *sensor);
 void rkisp1_csi_stop(struct rkisp1_csi *csi);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 253220188abd..faf2cd4c8149 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 
 static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
 {
+	rkisp1_csi_unregister(rkisp1);
 	rkisp1_params_unregister(rkisp1);
 	rkisp1_stats_unregister(rkisp1);
 	rkisp1_capture_devs_unregister(rkisp1);
@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
+	ret = rkisp1_csi_register(rkisp1);
+	if (ret)
+		goto error;
+
 	ret = rkisp1_create_links(rkisp1);
 	if (ret)
 		goto error;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Paul Elder

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Connect the CSI receiver subdevice into the rest of the driver. This
includes:
- calling the subdevice via the v4l2 subdev API
- moving the async notifier for the sensor from the ISP to the CSI
  receiver
- in the ISP, create a media link to the CSI receiver, and remove the
  media link creation to the sensor
- in the CSI receiver, create a media link to the sensor

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
 4 files changed, 53 insertions(+), 44 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 8182694a6fe0..96712b467dde 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
 		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
 }
 
+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
+			   struct rkisp1_sensor_async *s_asd,
+			   unsigned int source_pad)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+	int ret;		
+
+	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
+						V4L2_CID_PIXEL_RATE);
+	if (!s_asd->pixel_rate_ctrl) {
+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
+			sd->name);
+		return -EINVAL;
+	}
+
+	/* Create the link from the sensor to the CSI receiver. */
+	ret = media_create_pad_link(&sd->entity, source_pad,
+				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
+				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
+	if (ret) {
+		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
+			sd->name);
+		return ret;
+	}
+
+	return 0;
+}
+
 static int rkisp1_csi_config(struct rkisp1_csi *csi,
 			     const struct rkisp1_sensor_async *sensor)
 {
@@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
 }
 
-int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     const struct rkisp1_sensor_async *sensor)
+static int rkisp1_csi_start(struct rkisp1_csi *csi,
+			    const struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	union phy_configure_opts opts;
@@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
 	return 0;
 }
 
-void rkisp1_csi_stop(struct rkisp1_csi *csi)
+static void rkisp1_csi_stop(struct rkisp1_csi *csi)
 {
 	rkisp1_csi_disable(csi);
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index ddf8e5e08f55..eadcd24f65fb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 int rkisp1_csi_register(struct rkisp1_device *rkisp1);
 void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
 
-int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     const struct rkisp1_sensor_async *sensor);
-void rkisp1_csi_stop(struct rkisp1_csi *csi);
+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
+			   struct rkisp1_sensor_async *s_asd,
+			   unsigned int source_pad);
 
 #endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index faf2cd4c8149..a3e182c86bdd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -17,6 +17,7 @@
 #include <linux/pinctrl/consumer.h>
 #include <linux/pm_runtime.h>
 #include <media/v4l2-fwnode.h>
+#include <media/v4l2-mc.h>
 
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
@@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		container_of(asd, struct rkisp1_sensor_async, asd);
 	int source_pad;
 
-	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
-						V4L2_CID_PIXEL_RATE);
-	if (!s_asd->pixel_rate_ctrl) {
-		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
-			sd->name);
-		return -EINVAL;
-	}
-
 	s_asd->sd = sd;
 
-	/* Create the link to the sensor. */
 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
 						 MEDIA_PAD_FL_SOURCE);
 	if (source_pad < 0) {
@@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		return source_pad;
 	}
 
-	return media_create_pad_link(&sd->entity, source_pad,
-				     &rkisp1->isp.sd.entity,
-				     RKISP1_ISP_PAD_SINK_VIDEO,
-				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
+	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
 }
 
 static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
@@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 	unsigned int i;
 	int ret;
 
+	/* Link the CSI receiver to the ISP. */
+	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_VIDEO,
+				    MEDIA_LNK_FL_ENABLED);
+	if (ret)
+		return ret;
+
 	/* create ISP->RSZ->CAP links */
 	for (i = 0; i < 2; i++) {
 		struct media_entity *resizer =
@@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
-	ret = rkisp1_subdev_notifier_register(rkisp1);
-	if (ret) {
-		dev_err(rkisp1->dev,
-			"Failed to register subdev notifier(%d)\n", ret);
-		goto error;
-	}
-
 	return 0;
 
 error:
@@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
 	if (ret)
 		goto err_cleanup_csi;
 
+	ret = rkisp1_subdev_notifier_register(rkisp1);
+	if (ret)
+		goto err_unreg_entities;
+
 	rkisp1_debug_init(rkisp1);
 
 	return 0;
 
+err_unreg_entities:
+	rkisp1_entities_unregister(rkisp1);
 err_cleanup_csi:
 	rkisp1_csi_cleanup(rkisp1);
 err_unreg_media_dev:
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 5afb8be311c7..260c9ce0dca4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -16,7 +16,6 @@
 #include <media/v4l2-event.h>
 
 #include "rkisp1-common.h"
-#include "rkisp1-csi.h"
 
 #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
 #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
@@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	const struct rkisp1_sensor_async *asd;
 	struct media_pad *source_pad;
 	int ret;
 
 	if (!enable) {
 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
-
-		rkisp1_csi_stop(&rkisp1->csi);
 		rkisp1_isp_stop(isp);
-
 		return 0;
 	}
 
@@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return -EPIPE;
 	}
 
-	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
-			   asd);
-
-	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
-		return -EINVAL;
+	if (rkisp1->source != &rkisp1->csi.sd)
+		return -EPIPE;
 
 	isp->frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
+	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
 	if (ret)
 		goto mutex_unlock;
 
 	rkisp1_isp_start(isp);
 
-	ret = rkisp1_csi_start(&rkisp1->csi, asd);
-	if (ret) {
-		rkisp1_isp_stop(isp);
-		goto mutex_unlock;
-	}
-
 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
 		rkisp1_isp_stop(isp);
-		rkisp1_csi_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Paul Elder

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Connect the CSI receiver subdevice into the rest of the driver. This
includes:
- calling the subdevice via the v4l2 subdev API
- moving the async notifier for the sensor from the ISP to the CSI
  receiver
- in the ISP, create a media link to the CSI receiver, and remove the
  media link creation to the sensor
- in the CSI receiver, create a media link to the sensor

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
 .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
 4 files changed, 53 insertions(+), 44 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
index 8182694a6fe0..96712b467dde 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
@@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
 		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
 }
 
+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
+			   struct rkisp1_sensor_async *s_asd,
+			   unsigned int source_pad)
+{
+	struct rkisp1_csi *csi = &rkisp1->csi;
+	int ret;		
+
+	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
+						V4L2_CID_PIXEL_RATE);
+	if (!s_asd->pixel_rate_ctrl) {
+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
+			sd->name);
+		return -EINVAL;
+	}
+
+	/* Create the link from the sensor to the CSI receiver. */
+	ret = media_create_pad_link(&sd->entity, source_pad,
+				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
+				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
+	if (ret) {
+		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
+			sd->name);
+		return ret;
+	}
+
+	return 0;
+}
+
 static int rkisp1_csi_config(struct rkisp1_csi *csi,
 			     const struct rkisp1_sensor_async *sensor)
 {
@@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
 }
 
-int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     const struct rkisp1_sensor_async *sensor)
+static int rkisp1_csi_start(struct rkisp1_csi *csi,
+			    const struct rkisp1_sensor_async *sensor)
 {
 	struct rkisp1_device *rkisp1 = csi->rkisp1;
 	union phy_configure_opts opts;
@@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
 	return 0;
 }
 
-void rkisp1_csi_stop(struct rkisp1_csi *csi)
+static void rkisp1_csi_stop(struct rkisp1_csi *csi)
 {
 	rkisp1_csi_disable(csi);
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
index ddf8e5e08f55..eadcd24f65fb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
@@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
 int rkisp1_csi_register(struct rkisp1_device *rkisp1);
 void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
 
-int rkisp1_csi_start(struct rkisp1_csi *csi,
-		     const struct rkisp1_sensor_async *sensor);
-void rkisp1_csi_stop(struct rkisp1_csi *csi);
+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
+			   struct rkisp1_sensor_async *s_asd,
+			   unsigned int source_pad);
 
 #endif /* _RKISP1_CSI_H */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index faf2cd4c8149..a3e182c86bdd 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -17,6 +17,7 @@
 #include <linux/pinctrl/consumer.h>
 #include <linux/pm_runtime.h>
 #include <media/v4l2-fwnode.h>
+#include <media/v4l2-mc.h>
 
 #include "rkisp1-common.h"
 #include "rkisp1-csi.h"
@@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		container_of(asd, struct rkisp1_sensor_async, asd);
 	int source_pad;
 
-	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
-						V4L2_CID_PIXEL_RATE);
-	if (!s_asd->pixel_rate_ctrl) {
-		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
-			sd->name);
-		return -EINVAL;
-	}
-
 	s_asd->sd = sd;
 
-	/* Create the link to the sensor. */
 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
 						 MEDIA_PAD_FL_SOURCE);
 	if (source_pad < 0) {
@@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		return source_pad;
 	}
 
-	return media_create_pad_link(&sd->entity, source_pad,
-				     &rkisp1->isp.sd.entity,
-				     RKISP1_ISP_PAD_SINK_VIDEO,
-				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
+	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
 }
 
 static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
@@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 	unsigned int i;
 	int ret;
 
+	/* Link the CSI receiver to the ISP. */
+	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_VIDEO,
+				    MEDIA_LNK_FL_ENABLED);
+	if (ret)
+		return ret;
+
 	/* create ISP->RSZ->CAP links */
 	for (i = 0; i < 2; i++) {
 		struct media_entity *resizer =
@@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
-	ret = rkisp1_subdev_notifier_register(rkisp1);
-	if (ret) {
-		dev_err(rkisp1->dev,
-			"Failed to register subdev notifier(%d)\n", ret);
-		goto error;
-	}
-
 	return 0;
 
 error:
@@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
 	if (ret)
 		goto err_cleanup_csi;
 
+	ret = rkisp1_subdev_notifier_register(rkisp1);
+	if (ret)
+		goto err_unreg_entities;
+
 	rkisp1_debug_init(rkisp1);
 
 	return 0;
 
+err_unreg_entities:
+	rkisp1_entities_unregister(rkisp1);
 err_cleanup_csi:
 	rkisp1_csi_cleanup(rkisp1);
 err_unreg_media_dev:
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 5afb8be311c7..260c9ce0dca4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -16,7 +16,6 @@
 #include <media/v4l2-event.h>
 
 #include "rkisp1-common.h"
-#include "rkisp1-csi.h"
 
 #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
 #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
@@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 {
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
-	const struct rkisp1_sensor_async *asd;
 	struct media_pad *source_pad;
 	int ret;
 
 	if (!enable) {
 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
-
-		rkisp1_csi_stop(&rkisp1->csi);
 		rkisp1_isp_stop(isp);
-
 		return 0;
 	}
 
@@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return -EPIPE;
 	}
 
-	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
-			   asd);
-
-	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
-		return -EINVAL;
+	if (rkisp1->source != &rkisp1->csi.sd)
+		return -EPIPE;
 
 	isp->frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
+	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
 	if (ret)
 		goto mutex_unlock;
 
 	rkisp1_isp_start(isp);
 
-	ret = rkisp1_csi_start(&rkisp1->csi, asd);
-	if (ret) {
-		rkisp1_isp_stop(isp);
-		goto mutex_unlock;
-	}
-
 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
 		rkisp1_isp_stop(isp);
-		rkisp1_csi_stop(&rkisp1->csi);
 		goto mutex_unlock;
 	}
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 42/55] media: rkisp1: Use fwnode_graph_for_each_endpoint
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

When registering the notifier, replace the manual while loop with
fwnode_graph_for_each_endpoint. This simplifies error handling.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 44 +++++++++----------
 1 file changed, 20 insertions(+), 24 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index a3e182c86bdd..00ace8224575 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -158,29 +158,28 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
 static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
-	unsigned int next_id = 0;
+	struct fwnode_handle *fwnode = dev_fwnode(rkisp1->dev);
+	struct fwnode_handle *ep;
 	unsigned int index = 0;
-	int ret;
+	int ret = 0;
 
 	v4l2_async_nf_init(ntf);
 
-	while (1) {
+	ntf->ops = &rkisp1_subdev_notifier_ops;
+
+	fwnode_graph_for_each_endpoint(fwnode, ep) {
 		struct v4l2_fwnode_endpoint vep = {
 			.bus_type = V4L2_MBUS_CSI2_DPHY
 		};
 		struct rkisp1_sensor_async *rk_asd;
-		struct fwnode_handle *source = NULL;
-		struct fwnode_handle *ep;
-
-		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
-						     0, next_id,
-						     FWNODE_GRAPH_ENDPOINT_NEXT);
-		if (!ep)
-			break;
+		struct fwnode_handle *source;
 
 		ret = v4l2_fwnode_endpoint_parse(ep, &vep);
-		if (ret)
-			goto err_parse;
+		if (ret) {
+			dev_err(rkisp1->dev, "failed to parse endpoint %pfw\n",
+				ep);
+			break;
+		}
 
 		source = fwnode_graph_get_remote_endpoint(ep);
 		if (!source) {
@@ -188,14 +187,15 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 				"endpoint %pfw has no remote endpoint\n",
 				ep);
 			ret = -ENODEV;
-			goto err_parse;
+			break;
 		}
 
 		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
 						  struct rkisp1_sensor_async);
 		if (IS_ERR(rk_asd)) {
+			fwnode_handle_put(source);
 			ret = PTR_ERR(rk_asd);
-			goto err_parse;
+			break;
 		}
 
 		rk_asd->index = index++;
@@ -206,27 +206,23 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 
 		dev_dbg(rkisp1->dev, "registered ep id %d with %d lanes\n",
 			vep.base.id, rk_asd->lanes);
+	}
 
-		next_id = vep.base.id + 1;
-
-		fwnode_handle_put(ep);
-
-		continue;
-err_parse:
+	if (ret) {
 		fwnode_handle_put(ep);
-		fwnode_handle_put(source);
 		v4l2_async_nf_cleanup(ntf);
 		return ret;
 	}
 
-	if (next_id == 0)
+	if (!index)
 		dev_dbg(rkisp1->dev, "no remote subdevice found\n");
-	ntf->ops = &rkisp1_subdev_notifier_ops;
+
 	ret = v4l2_async_nf_register(&rkisp1->v4l2_dev, ntf);
 	if (ret) {
 		v4l2_async_nf_cleanup(ntf);
 		return ret;
 	}
+
 	return 0;
 }
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 42/55] media: rkisp1: Use fwnode_graph_for_each_endpoint
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

When registering the notifier, replace the manual while loop with
fwnode_graph_for_each_endpoint. This simplifies error handling.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 44 +++++++++----------
 1 file changed, 20 insertions(+), 24 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index a3e182c86bdd..00ace8224575 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -158,29 +158,28 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
 static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 {
 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
-	unsigned int next_id = 0;
+	struct fwnode_handle *fwnode = dev_fwnode(rkisp1->dev);
+	struct fwnode_handle *ep;
 	unsigned int index = 0;
-	int ret;
+	int ret = 0;
 
 	v4l2_async_nf_init(ntf);
 
-	while (1) {
+	ntf->ops = &rkisp1_subdev_notifier_ops;
+
+	fwnode_graph_for_each_endpoint(fwnode, ep) {
 		struct v4l2_fwnode_endpoint vep = {
 			.bus_type = V4L2_MBUS_CSI2_DPHY
 		};
 		struct rkisp1_sensor_async *rk_asd;
-		struct fwnode_handle *source = NULL;
-		struct fwnode_handle *ep;
-
-		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
-						     0, next_id,
-						     FWNODE_GRAPH_ENDPOINT_NEXT);
-		if (!ep)
-			break;
+		struct fwnode_handle *source;
 
 		ret = v4l2_fwnode_endpoint_parse(ep, &vep);
-		if (ret)
-			goto err_parse;
+		if (ret) {
+			dev_err(rkisp1->dev, "failed to parse endpoint %pfw\n",
+				ep);
+			break;
+		}
 
 		source = fwnode_graph_get_remote_endpoint(ep);
 		if (!source) {
@@ -188,14 +187,15 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 				"endpoint %pfw has no remote endpoint\n",
 				ep);
 			ret = -ENODEV;
-			goto err_parse;
+			break;
 		}
 
 		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
 						  struct rkisp1_sensor_async);
 		if (IS_ERR(rk_asd)) {
+			fwnode_handle_put(source);
 			ret = PTR_ERR(rk_asd);
-			goto err_parse;
+			break;
 		}
 
 		rk_asd->index = index++;
@@ -206,27 +206,23 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 
 		dev_dbg(rkisp1->dev, "registered ep id %d with %d lanes\n",
 			vep.base.id, rk_asd->lanes);
+	}
 
-		next_id = vep.base.id + 1;
-
-		fwnode_handle_put(ep);
-
-		continue;
-err_parse:
+	if (ret) {
 		fwnode_handle_put(ep);
-		fwnode_handle_put(source);
 		v4l2_async_nf_cleanup(ntf);
 		return ret;
 	}
 
-	if (next_id == 0)
+	if (!index)
 		dev_dbg(rkisp1->dev, "no remote subdevice found\n");
-	ntf->ops = &rkisp1_subdev_notifier_ops;
+
 	ret = v4l2_async_nf_register(&rkisp1->v4l2_dev, ntf);
 	if (ret) {
 		v4l2_async_nf_cleanup(ntf);
 		return ret;
 	}
+
 	return 0;
 }
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The rkisp1 can take an input on the parallel interface. Add a port for
it, and update the required field. At least one port is required, and
both may be specified.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
 1 file changed, 21 insertions(+), 2 deletions(-)

diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
index d1489b177331..b3661d7d4357 100644
--- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
+++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
@@ -84,8 +84,27 @@ properties:
                 minItems: 1
                 maxItems: 4
 
-    required:
-      - port@0
+      port@1:
+        $ref: /schemas/graph.yaml#/$defs/port-base
+        unevaluatedProperties: false
+        description: connection point for input on the parallel interface
+
+        properties:
+          bus-type:
+            enum: [5, 6]
+
+          endpoint:
+            $ref: video-interfaces.yaml#
+            unevaluatedProperties: false
+
+        required:
+          - bus-type
+
+    anyOf:
+      - required:
+          - port@0
+      - required:
+          - port@1
 
 required:
   - compatible
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The rkisp1 can take an input on the parallel interface. Add a port for
it, and update the required field. At least one port is required, and
both may be specified.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
 1 file changed, 21 insertions(+), 2 deletions(-)

diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
index d1489b177331..b3661d7d4357 100644
--- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
+++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
@@ -84,8 +84,27 @@ properties:
                 minItems: 1
                 maxItems: 4
 
-    required:
-      - port@0
+      port@1:
+        $ref: /schemas/graph.yaml#/$defs/port-base
+        unevaluatedProperties: false
+        description: connection point for input on the parallel interface
+
+        properties:
+          bus-type:
+            enum: [5, 6]
+
+          endpoint:
+            $ref: video-interfaces.yaml#
+            unevaluatedProperties: false
+
+        required:
+          - bus-type
+
+    anyOf:
+      - required:
+          - port@0
+      - required:
+          - port@1
 
 required:
   - compatible
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 44/55] media: rkisp1: Support the ISP parallel input
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP has a parallel input, exposed through port 1 in the device tree
node. While the driver supports configuring the ISP for the parallel and
BT.656 input modes, the DT parsing code, the subdev bound handler and
the ISP stream start handler only support the CSI input. Extend them to
support the parallel input.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 68 ++++++++++++++++---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 18 ++++-
 3 files changed, 77 insertions(+), 11 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 0ab49d1feb55..f926ca8248f8 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -130,6 +130,7 @@ struct rkisp1_info {
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
  * @sd:			a pointer to v4l2_subdev struct of the sensor
  * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
+ * @port:		port number (0: MIPI, 1: Parallel)
  */
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
@@ -140,6 +141,7 @@ struct rkisp1_sensor_async {
 	unsigned int mbus_flags;
 	struct v4l2_subdev *sd;
 	struct v4l2_ctrl *pixel_rate_ctrl;
+	unsigned int port;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 00ace8224575..e85cf0d79af9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -119,6 +119,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 	struct rkisp1_sensor_async *s_asd =
 		container_of(asd, struct rkisp1_sensor_async, asd);
 	int source_pad;
+	int ret;
 
 	s_asd->sd = sd;
 
@@ -130,7 +131,20 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		return source_pad;
 	}
 
-	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
+	if (s_asd->port == 0)
+		return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
+
+	ret = media_create_pad_link(&sd->entity, source_pad,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_VIDEO,
+				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
+	if (ret) {
+		dev_err(rkisp1->dev, "failed to link source pad of %s\n",
+			sd->name);
+		return ret;
+	}
+
+	return 0;
 }
 
 static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
@@ -168,12 +182,33 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 	ntf->ops = &rkisp1_subdev_notifier_ops;
 
 	fwnode_graph_for_each_endpoint(fwnode, ep) {
-		struct v4l2_fwnode_endpoint vep = {
-			.bus_type = V4L2_MBUS_CSI2_DPHY
-		};
+		struct fwnode_handle *port;
+		struct v4l2_fwnode_endpoint vep = { };
 		struct rkisp1_sensor_async *rk_asd;
 		struct fwnode_handle *source;
+		u32 reg = 0;
 
+		/* Select the bus type based on the port. */
+		port = fwnode_get_parent(ep);
+		fwnode_property_read_u32(port, "reg", &reg);
+		fwnode_handle_put(port);
+
+		switch (reg) {
+		case 0:
+			vep.bus_type = V4L2_MBUS_CSI2_DPHY;
+			break;
+
+		case 1:
+			/*
+			 * Parallel port. The bus-type property in DT is
+			 * mandatory for port 1, it will be used to determine if
+			 * it's PARALLEL or BT656.
+			 */
+			vep.bus_type = V4L2_MBUS_UNKNOWN;
+			break;
+		}
+
+		/* Parse the endpoint and validate the bus type. */
 		ret = v4l2_fwnode_endpoint_parse(ep, &vep);
 		if (ret) {
 			dev_err(rkisp1->dev, "failed to parse endpoint %pfw\n",
@@ -181,6 +216,17 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 			break;
 		}
 
+		if (vep.base.port == 1) {
+			if (vep.bus_type != V4L2_MBUS_PARALLEL &&
+			    vep.bus_type != V4L2_MBUS_BT656) {
+				dev_err(rkisp1->dev,
+					"port 1 must be parallel or BT656\n");
+				ret = -EINVAL;
+				break;
+			}
+		}
+
+		/* Add the async subdev to the notifier. */
 		source = fwnode_graph_get_remote_endpoint(ep);
 		if (!source) {
 			dev_err(rkisp1->dev,
@@ -201,11 +247,17 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 		rk_asd->index = index++;
 		rk_asd->source_ep = source;
 		rk_asd->mbus_type = vep.bus_type;
-		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
-		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
+		rk_asd->port = vep.base.port;
+
+		if (vep.bus_type == V4L2_MBUS_CSI2_DPHY) {
+			rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
+			rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
+		} else {
+			rk_asd->mbus_flags = vep.bus.parallel.flags;
+		}
 
-		dev_dbg(rkisp1->dev, "registered ep id %d with %d lanes\n",
-			vep.base.id, rk_asd->lanes);
+		dev_dbg(rkisp1->dev, "registered ep id %d, bus type %u, %u lanes\n",
+			vep.base.id, rk_asd->mbus_type, rk_asd->lanes);
 	}
 
 	if (ret) {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 260c9ce0dca4..8268331faca9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -728,6 +728,8 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	struct media_pad *source_pad;
+	enum v4l2_mbus_type mbus_type;
+	u32 mbus_flags;
 	int ret;
 
 	if (!enable) {
@@ -749,12 +751,22 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return -EPIPE;
 	}
 
-	if (rkisp1->source != &rkisp1->csi.sd)
-		return -EPIPE;
+	if (rkisp1->source == &rkisp1->csi.sd) {
+		mbus_type = V4L2_MBUS_CSI2_DPHY;
+		mbus_flags = 0;
+	} else {
+		const struct rkisp1_sensor_async *asd;
+
+		asd = container_of(rkisp1->source->asd,
+				   struct rkisp1_sensor_async, asd);
+
+		mbus_type = asd->mbus_type;
+		mbus_flags = asd->mbus_flags;
+	}
 
 	isp->frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
+	ret = rkisp1_config_cif(isp, mbus_type, mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 44/55] media: rkisp1: Support the ISP parallel input
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP has a parallel input, exposed through port 1 in the device tree
node. While the driver supports configuring the ISP for the parallel and
BT.656 input modes, the DT parsing code, the subdev bound handler and
the ISP stream start handler only support the CSI input. Extend them to
support the parallel input.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 68 ++++++++++++++++---
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 18 ++++-
 3 files changed, 77 insertions(+), 11 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 0ab49d1feb55..f926ca8248f8 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -130,6 +130,7 @@ struct rkisp1_info {
  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
  * @sd:			a pointer to v4l2_subdev struct of the sensor
  * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
+ * @port:		port number (0: MIPI, 1: Parallel)
  */
 struct rkisp1_sensor_async {
 	struct v4l2_async_subdev asd;
@@ -140,6 +141,7 @@ struct rkisp1_sensor_async {
 	unsigned int mbus_flags;
 	struct v4l2_subdev *sd;
 	struct v4l2_ctrl *pixel_rate_ctrl;
+	unsigned int port;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 00ace8224575..e85cf0d79af9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -119,6 +119,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 	struct rkisp1_sensor_async *s_asd =
 		container_of(asd, struct rkisp1_sensor_async, asd);
 	int source_pad;
+	int ret;
 
 	s_asd->sd = sd;
 
@@ -130,7 +131,20 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
 		return source_pad;
 	}
 
-	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
+	if (s_asd->port == 0)
+		return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
+
+	ret = media_create_pad_link(&sd->entity, source_pad,
+				    &rkisp1->isp.sd.entity,
+				    RKISP1_ISP_PAD_SINK_VIDEO,
+				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
+	if (ret) {
+		dev_err(rkisp1->dev, "failed to link source pad of %s\n",
+			sd->name);
+		return ret;
+	}
+
+	return 0;
 }
 
 static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
@@ -168,12 +182,33 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 	ntf->ops = &rkisp1_subdev_notifier_ops;
 
 	fwnode_graph_for_each_endpoint(fwnode, ep) {
-		struct v4l2_fwnode_endpoint vep = {
-			.bus_type = V4L2_MBUS_CSI2_DPHY
-		};
+		struct fwnode_handle *port;
+		struct v4l2_fwnode_endpoint vep = { };
 		struct rkisp1_sensor_async *rk_asd;
 		struct fwnode_handle *source;
+		u32 reg = 0;
 
+		/* Select the bus type based on the port. */
+		port = fwnode_get_parent(ep);
+		fwnode_property_read_u32(port, "reg", &reg);
+		fwnode_handle_put(port);
+
+		switch (reg) {
+		case 0:
+			vep.bus_type = V4L2_MBUS_CSI2_DPHY;
+			break;
+
+		case 1:
+			/*
+			 * Parallel port. The bus-type property in DT is
+			 * mandatory for port 1, it will be used to determine if
+			 * it's PARALLEL or BT656.
+			 */
+			vep.bus_type = V4L2_MBUS_UNKNOWN;
+			break;
+		}
+
+		/* Parse the endpoint and validate the bus type. */
 		ret = v4l2_fwnode_endpoint_parse(ep, &vep);
 		if (ret) {
 			dev_err(rkisp1->dev, "failed to parse endpoint %pfw\n",
@@ -181,6 +216,17 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 			break;
 		}
 
+		if (vep.base.port == 1) {
+			if (vep.bus_type != V4L2_MBUS_PARALLEL &&
+			    vep.bus_type != V4L2_MBUS_BT656) {
+				dev_err(rkisp1->dev,
+					"port 1 must be parallel or BT656\n");
+				ret = -EINVAL;
+				break;
+			}
+		}
+
+		/* Add the async subdev to the notifier. */
 		source = fwnode_graph_get_remote_endpoint(ep);
 		if (!source) {
 			dev_err(rkisp1->dev,
@@ -201,11 +247,17 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 		rk_asd->index = index++;
 		rk_asd->source_ep = source;
 		rk_asd->mbus_type = vep.bus_type;
-		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
-		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
+		rk_asd->port = vep.base.port;
+
+		if (vep.bus_type == V4L2_MBUS_CSI2_DPHY) {
+			rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
+			rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
+		} else {
+			rk_asd->mbus_flags = vep.bus.parallel.flags;
+		}
 
-		dev_dbg(rkisp1->dev, "registered ep id %d with %d lanes\n",
-			vep.base.id, rk_asd->lanes);
+		dev_dbg(rkisp1->dev, "registered ep id %d, bus type %u, %u lanes\n",
+			vep.base.id, rk_asd->mbus_type, rk_asd->lanes);
 	}
 
 	if (ret) {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 260c9ce0dca4..8268331faca9 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -728,6 +728,8 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	struct media_pad *source_pad;
+	enum v4l2_mbus_type mbus_type;
+	u32 mbus_flags;
 	int ret;
 
 	if (!enable) {
@@ -749,12 +751,22 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 		return -EPIPE;
 	}
 
-	if (rkisp1->source != &rkisp1->csi.sd)
-		return -EPIPE;
+	if (rkisp1->source == &rkisp1->csi.sd) {
+		mbus_type = V4L2_MBUS_CSI2_DPHY;
+		mbus_flags = 0;
+	} else {
+		const struct rkisp1_sensor_async *asd;
+
+		asd = container_of(rkisp1->source->asd,
+				   struct rkisp1_sensor_async, asd);
+
+		mbus_type = asd->mbus_type;
+		mbus_flags = asd->mbus_flags;
+	}
 
 	isp->frame_sequence = -1;
 	mutex_lock(&isp->ops_lock);
-	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
+	ret = rkisp1_config_cif(isp, mbus_type, mbus_flags);
 	if (ret)
 		goto mutex_unlock;
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 45/55] media: rkisp1: Add infrastructure to support ISP features
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Different ISP versions implement different sets of features. The driver
already takes the version into account in several places, but this
approach won't scale well for features that are found in different
versions. Introduce a new mechanism using a features bitmask in the
rkisp1_info structure to indicate which features the ISP support.

The first feature bit tells if the ISP has an internal CSI-2 receiver,
which is not available in all ISP versions.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h      | 15 +++++++++++++++
 .../media/platform/rockchip/rkisp1/rkisp1-dev.c   |  2 ++
 2 files changed, 17 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index f926ca8248f8..eccdd3f9bc89 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -98,6 +98,19 @@ enum rkisp1_isp_pad {
 	RKISP1_ISP_PAD_MAX
 };
 
+/*
+ * enum rkisp1_feature - ISP features
+ *
+ * @RKISP1_FEATURE_MIPI_CSI2: The ISP has an internal MIPI CSI-2 receiver
+ *
+ * The ISP features are stored in a bitmask in &rkisp1_info.features and allow
+ * the driver to implement support for features present in some ISP versions
+ * only.
+ */
+enum rkisp1_feature {
+	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
+};
+
 /*
  * struct rkisp1_info - Model-specific ISP Information
  *
@@ -106,6 +119,7 @@ enum rkisp1_isp_pad {
  * @isrs: array of ISP interrupt descriptors
  * @isr_size: number of entires in the @isrs array
  * @isp_ver: ISP version
+ * @features: bitmatk of rkisp1_feature features implemented by the ISP
  *
  * This structure contains information about the ISP specific to a particular
  * ISP model, version, or integration in a particular SoC.
@@ -116,6 +130,7 @@ struct rkisp1_info {
 	const struct rkisp1_isr_data *isrs;
 	unsigned int isr_size;
 	enum rkisp1_cif_isp_version isp_ver;
+	unsigned int features;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index e85cf0d79af9..8ccd4042f3f3 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -450,6 +450,7 @@ static const struct rkisp1_info px30_isp_info = {
 	.isrs = px30_isp_isrs,
 	.isr_size = ARRAY_SIZE(px30_isp_isrs),
 	.isp_ver = RKISP1_V12,
+	.features = RKISP1_FEATURE_MIPI_CSI2,
 };
 
 static const char * const rk3399_isp_clks[] = {
@@ -468,6 +469,7 @@ static const struct rkisp1_info rk3399_isp_info = {
 	.isrs = rk3399_isp_isrs,
 	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
 	.isp_ver = RKISP1_V10,
+	.features = RKISP1_FEATURE_MIPI_CSI2,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 45/55] media: rkisp1: Add infrastructure to support ISP features
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Different ISP versions implement different sets of features. The driver
already takes the version into account in several places, but this
approach won't scale well for features that are found in different
versions. Introduce a new mechanism using a features bitmask in the
rkisp1_info structure to indicate which features the ISP support.

The first feature bit tells if the ISP has an internal CSI-2 receiver,
which is not available in all ISP versions.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h      | 15 +++++++++++++++
 .../media/platform/rockchip/rkisp1/rkisp1-dev.c   |  2 ++
 2 files changed, 17 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index f926ca8248f8..eccdd3f9bc89 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -98,6 +98,19 @@ enum rkisp1_isp_pad {
 	RKISP1_ISP_PAD_MAX
 };
 
+/*
+ * enum rkisp1_feature - ISP features
+ *
+ * @RKISP1_FEATURE_MIPI_CSI2: The ISP has an internal MIPI CSI-2 receiver
+ *
+ * The ISP features are stored in a bitmask in &rkisp1_info.features and allow
+ * the driver to implement support for features present in some ISP versions
+ * only.
+ */
+enum rkisp1_feature {
+	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
+};
+
 /*
  * struct rkisp1_info - Model-specific ISP Information
  *
@@ -106,6 +119,7 @@ enum rkisp1_isp_pad {
  * @isrs: array of ISP interrupt descriptors
  * @isr_size: number of entires in the @isrs array
  * @isp_ver: ISP version
+ * @features: bitmatk of rkisp1_feature features implemented by the ISP
  *
  * This structure contains information about the ISP specific to a particular
  * ISP model, version, or integration in a particular SoC.
@@ -116,6 +130,7 @@ struct rkisp1_info {
 	const struct rkisp1_isr_data *isrs;
 	unsigned int isr_size;
 	enum rkisp1_cif_isp_version isp_ver;
+	unsigned int features;
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index e85cf0d79af9..8ccd4042f3f3 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -450,6 +450,7 @@ static const struct rkisp1_info px30_isp_info = {
 	.isrs = px30_isp_isrs,
 	.isr_size = ARRAY_SIZE(px30_isp_isrs),
 	.isp_ver = RKISP1_V12,
+	.features = RKISP1_FEATURE_MIPI_CSI2,
 };
 
 static const char * const rk3399_isp_clks[] = {
@@ -468,6 +469,7 @@ static const struct rkisp1_info rk3399_isp_info = {
 	.isrs = rk3399_isp_isrs,
 	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
 	.isp_ver = RKISP1_V10,
+	.features = RKISP1_FEATURE_MIPI_CSI2,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 46/55] media: rkisp1: Make the internal CSI-2 receiver optional
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Not all ISP versions integrate a MIPI CSI-2 receiver.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 50 +++++++++++++------
 1 file changed, 34 insertions(+), 16 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 8ccd4042f3f3..62fa2bd275fe 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -195,6 +195,14 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 
 		switch (reg) {
 		case 0:
+			/* MIPI CSI-2 port */
+			if (!(rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)) {
+				dev_err(rkisp1->dev,
+					"internal CSI must be available for port 0\n");
+				ret = -EINVAL;
+				break;
+			}
+
 			vep.bus_type = V4L2_MBUS_CSI2_DPHY;
 			break;
 
@@ -320,13 +328,16 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 	unsigned int i;
 	int ret;
 
-	/* Link the CSI receiver to the ISP. */
-	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
-				    &rkisp1->isp.sd.entity,
-				    RKISP1_ISP_PAD_SINK_VIDEO,
-				    MEDIA_LNK_FL_ENABLED);
-	if (ret)
-		return ret;
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2) {
+		/* Link the CSI receiver to the ISP. */
+		ret = media_create_pad_link(&rkisp1->csi.sd.entity,
+					    RKISP1_CSI_PAD_SRC,
+					    &rkisp1->isp.sd.entity,
+					    RKISP1_ISP_PAD_SINK_VIDEO,
+					    MEDIA_LNK_FL_ENABLED);
+		if (ret)
+			return ret;
+	}
 
 	/* create ISP->RSZ->CAP links */
 	for (i = 0; i < 2; i++) {
@@ -369,7 +380,8 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 
 static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
 {
-	rkisp1_csi_unregister(rkisp1);
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)
+		rkisp1_csi_unregister(rkisp1);
 	rkisp1_params_unregister(rkisp1);
 	rkisp1_stats_unregister(rkisp1);
 	rkisp1_capture_devs_unregister(rkisp1);
@@ -401,9 +413,11 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
-	ret = rkisp1_csi_register(rkisp1);
-	if (ret)
-		goto error;
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2) {
+		ret = rkisp1_csi_register(rkisp1);
+		if (ret)
+			goto error;
+	}
 
 	ret = rkisp1_create_links(rkisp1);
 	if (ret)
@@ -566,9 +580,11 @@ static int rkisp1_probe(struct platform_device *pdev)
 		goto err_unreg_v4l2_dev;
 	}
 
-	ret = rkisp1_csi_init(rkisp1);
-	if (ret)
-		goto err_unreg_media_dev;
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2) {
+		ret = rkisp1_csi_init(rkisp1);
+		if (ret)
+			goto err_unreg_media_dev;
+	}
 
 	ret = rkisp1_entities_register(rkisp1);
 	if (ret)
@@ -585,7 +601,8 @@ static int rkisp1_probe(struct platform_device *pdev)
 err_unreg_entities:
 	rkisp1_entities_unregister(rkisp1);
 err_cleanup_csi:
-	rkisp1_csi_cleanup(rkisp1);
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)
+		rkisp1_csi_cleanup(rkisp1);
 err_unreg_media_dev:
 	media_device_unregister(&rkisp1->media_dev);
 err_unreg_v4l2_dev:
@@ -603,7 +620,8 @@ static int rkisp1_remove(struct platform_device *pdev)
 	v4l2_async_nf_cleanup(&rkisp1->notifier);
 
 	rkisp1_entities_unregister(rkisp1);
-	rkisp1_csi_cleanup(rkisp1);
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)
+		rkisp1_csi_cleanup(rkisp1);
 	rkisp1_debug_cleanup(rkisp1);
 
 	media_device_unregister(&rkisp1->media_dev);
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 46/55] media: rkisp1: Make the internal CSI-2 receiver optional
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Not all ISP versions integrate a MIPI CSI-2 receiver.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 50 +++++++++++++------
 1 file changed, 34 insertions(+), 16 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 8ccd4042f3f3..62fa2bd275fe 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -195,6 +195,14 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
 
 		switch (reg) {
 		case 0:
+			/* MIPI CSI-2 port */
+			if (!(rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)) {
+				dev_err(rkisp1->dev,
+					"internal CSI must be available for port 0\n");
+				ret = -EINVAL;
+				break;
+			}
+
 			vep.bus_type = V4L2_MBUS_CSI2_DPHY;
 			break;
 
@@ -320,13 +328,16 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 	unsigned int i;
 	int ret;
 
-	/* Link the CSI receiver to the ISP. */
-	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
-				    &rkisp1->isp.sd.entity,
-				    RKISP1_ISP_PAD_SINK_VIDEO,
-				    MEDIA_LNK_FL_ENABLED);
-	if (ret)
-		return ret;
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2) {
+		/* Link the CSI receiver to the ISP. */
+		ret = media_create_pad_link(&rkisp1->csi.sd.entity,
+					    RKISP1_CSI_PAD_SRC,
+					    &rkisp1->isp.sd.entity,
+					    RKISP1_ISP_PAD_SINK_VIDEO,
+					    MEDIA_LNK_FL_ENABLED);
+		if (ret)
+			return ret;
+	}
 
 	/* create ISP->RSZ->CAP links */
 	for (i = 0; i < 2; i++) {
@@ -369,7 +380,8 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
 
 static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
 {
-	rkisp1_csi_unregister(rkisp1);
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)
+		rkisp1_csi_unregister(rkisp1);
 	rkisp1_params_unregister(rkisp1);
 	rkisp1_stats_unregister(rkisp1);
 	rkisp1_capture_devs_unregister(rkisp1);
@@ -401,9 +413,11 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
 	if (ret)
 		goto error;
 
-	ret = rkisp1_csi_register(rkisp1);
-	if (ret)
-		goto error;
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2) {
+		ret = rkisp1_csi_register(rkisp1);
+		if (ret)
+			goto error;
+	}
 
 	ret = rkisp1_create_links(rkisp1);
 	if (ret)
@@ -566,9 +580,11 @@ static int rkisp1_probe(struct platform_device *pdev)
 		goto err_unreg_v4l2_dev;
 	}
 
-	ret = rkisp1_csi_init(rkisp1);
-	if (ret)
-		goto err_unreg_media_dev;
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2) {
+		ret = rkisp1_csi_init(rkisp1);
+		if (ret)
+			goto err_unreg_media_dev;
+	}
 
 	ret = rkisp1_entities_register(rkisp1);
 	if (ret)
@@ -585,7 +601,8 @@ static int rkisp1_probe(struct platform_device *pdev)
 err_unreg_entities:
 	rkisp1_entities_unregister(rkisp1);
 err_cleanup_csi:
-	rkisp1_csi_cleanup(rkisp1);
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)
+		rkisp1_csi_cleanup(rkisp1);
 err_unreg_media_dev:
 	media_device_unregister(&rkisp1->media_dev);
 err_unreg_v4l2_dev:
@@ -603,7 +620,8 @@ static int rkisp1_remove(struct platform_device *pdev)
 	v4l2_async_nf_cleanup(&rkisp1->notifier);
 
 	rkisp1_entities_unregister(rkisp1);
-	rkisp1_csi_cleanup(rkisp1);
+	if (rkisp1->info->features & RKISP1_FEATURE_MIPI_CSI2)
+		rkisp1_csi_cleanup(rkisp1);
 	rkisp1_debug_cleanup(rkisp1);
 
 	media_device_unregister(&rkisp1->media_dev);
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 47/55] dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The i.MX8MP ISP is compatbile with the rkisp1 driver. Add it to the list
of compatible strings. While at it, expand on the description of the
clocks to make it clear which clock in the i.MX8MP ISP they map to,
based on the names from the datasheet (which are confusing).

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 Documentation/devicetree/bindings/media/rockchip-isp1.yaml | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
index b3661d7d4357..95cf945f7ac5 100644
--- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
+++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
@@ -16,6 +16,7 @@ description: |
 properties:
   compatible:
     enum:
+      - fsl,imx8mp-isp
       - rockchip,px30-cif-isp
       - rockchip,rk3399-cif-isp
 
@@ -36,9 +37,9 @@ properties:
     minItems: 3
     items:
       # isp0 and isp1
-      - description: ISP clock
-      - description: ISP AXI clock
-      - description: ISP AHB clock
+      - description: ISP clock (for imx8mp, clk)
+      - description: ISP AXI clock (for imx8mp, m_hclk)
+      - description: ISP AHB clock (for imx8mp, hclk)
       # only for isp1
       - description: ISP Pixel clock
 
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 47/55] dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The i.MX8MP ISP is compatbile with the rkisp1 driver. Add it to the list
of compatible strings. While at it, expand on the description of the
clocks to make it clear which clock in the i.MX8MP ISP they map to,
based on the names from the datasheet (which are confusing).

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 Documentation/devicetree/bindings/media/rockchip-isp1.yaml | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
index b3661d7d4357..95cf945f7ac5 100644
--- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
+++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
@@ -16,6 +16,7 @@ description: |
 properties:
   compatible:
     enum:
+      - fsl,imx8mp-isp
       - rockchip,px30-cif-isp
       - rockchip,rk3399-cif-isp
 
@@ -36,9 +37,9 @@ properties:
     minItems: 3
     items:
       # isp0 and isp1
-      - description: ISP clock
-      - description: ISP AXI clock
-      - description: ISP AHB clock
+      - description: ISP clock (for imx8mp, clk)
+      - description: ISP AXI clock (for imx8mp, m_hclk)
+      - description: ISP AHB clock (for imx8mp, hclk)
       # only for isp1
       - description: ISP Pixel clock
 
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add match data to the rkisp1 driver to match the i.MX8MP ISP.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
 include/uapi/linux/rkisp1-config.h            |  3 +++
 2 files changed, 25 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 62fa2bd275fe..3a0115bdcee5 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
 	.features = RKISP1_FEATURE_MIPI_CSI2,
 };
 
+static const char * const imx8mp_isp_clks[] = {
+	"isp",
+	"hclk",
+	"aclk",
+};
+
+static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
+	{ NULL, rkisp1_isr },
+};
+
+static const struct rkisp1_info imx8mp_isp_info = {
+	.clks = imx8mp_isp_clks,
+	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
+	.isrs = imx8mp_isp_isrs,
+	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
+	.isp_ver = IMX8MP_V10,
+};
+
 static const struct of_device_id rkisp1_of_match[] = {
 	{
 		.compatible = "rockchip,px30-cif-isp",
@@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
 		.compatible = "rockchip,rk3399-cif-isp",
 		.data = &rk3399_isp_info,
 	},
+	{
+		.compatible = "fsl,imx8mp-isp",
+		.data = &imx8mp_isp_info,
+	},
 	{},
 };
 MODULE_DEVICE_TABLE(of, rkisp1_of_match);
diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
index 583ca0d9a79d..40677d47825c 100644
--- a/include/uapi/linux/rkisp1-config.h
+++ b/include/uapi/linux/rkisp1-config.h
@@ -140,12 +140,15 @@
  * @RKISP1_V11: declared in the original vendor code, but not used
  * @RKISP1_V12: used at least in rk3326 and px30
  * @RKISP1_V13: used at least in rk1808
+ * @IMX8MP_V10: used in at least imx8mp
  */
 enum rkisp1_cif_isp_version {
 	RKISP1_V10 = 10,
 	RKISP1_V11,
 	RKISP1_V12,
 	RKISP1_V13,
+	/* TODO Choose a better version for this */
+	IMX8MP_V10,
 };
 
 enum rkisp1_cif_isp_histogram_mode {
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add match data to the rkisp1 driver to match the i.MX8MP ISP.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
 include/uapi/linux/rkisp1-config.h            |  3 +++
 2 files changed, 25 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 62fa2bd275fe..3a0115bdcee5 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
 	.features = RKISP1_FEATURE_MIPI_CSI2,
 };
 
+static const char * const imx8mp_isp_clks[] = {
+	"isp",
+	"hclk",
+	"aclk",
+};
+
+static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
+	{ NULL, rkisp1_isr },
+};
+
+static const struct rkisp1_info imx8mp_isp_info = {
+	.clks = imx8mp_isp_clks,
+	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
+	.isrs = imx8mp_isp_isrs,
+	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
+	.isp_ver = IMX8MP_V10,
+};
+
 static const struct of_device_id rkisp1_of_match[] = {
 	{
 		.compatible = "rockchip,px30-cif-isp",
@@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
 		.compatible = "rockchip,rk3399-cif-isp",
 		.data = &rk3399_isp_info,
 	},
+	{
+		.compatible = "fsl,imx8mp-isp",
+		.data = &imx8mp_isp_info,
+	},
 	{},
 };
 MODULE_DEVICE_TABLE(of, rkisp1_of_match);
diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
index 583ca0d9a79d..40677d47825c 100644
--- a/include/uapi/linux/rkisp1-config.h
+++ b/include/uapi/linux/rkisp1-config.h
@@ -140,12 +140,15 @@
  * @RKISP1_V11: declared in the original vendor code, but not used
  * @RKISP1_V12: used at least in rk3326 and px30
  * @RKISP1_V13: used at least in rk1808
+ * @IMX8MP_V10: used in at least imx8mp
  */
 enum rkisp1_cif_isp_version {
 	RKISP1_V10 = 10,
 	RKISP1_V11,
 	RKISP1_V12,
 	RKISP1_V13,
+	/* TODO Choose a better version for this */
+	IMX8MP_V10,
 };
 
 enum rkisp1_cif_isp_histogram_mode {
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 49/55] media: rkisp1: Configure gasket on i.MX8MP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The i.MX8MP has a gasket between the CSI-2 receiver and the ISP.
Configure and enable it when starting the ISP, and disable it when
stopping.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |   5 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  16 +++
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 128 +++++++++++++++++-
 3 files changed, 147 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index eccdd3f9bc89..667fca0fef95 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -24,6 +24,7 @@
 #include "rkisp1-regs.h"
 
 struct dentry;
+struct regmap;
 
 /*
  * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
@@ -451,6 +452,8 @@ struct rkisp1_debug {
  * @dev:	   a pointer to the struct device
  * @clk_size:	   number of clocks
  * @clks:	   array of clocks
+ * @gasket:	   the gasket - i.MX8MP only
+ * @gasket_id:	   the gasket ID (0 or 1) - i.MX8MP only
  * @v4l2_dev:	   v4l2_device variable
  * @media_dev:	   media_device variable
  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
@@ -471,6 +474,8 @@ struct rkisp1_device {
 	struct device *dev;
 	unsigned int clk_size;
 	struct clk_bulk_data clks[RKISP1_MAX_BUS_CLK];
+	struct regmap *gasket;
+	unsigned int gasket_id;
 	struct v4l2_device v4l2_dev;
 	struct media_device media_dev;
 	struct v4l2_async_notifier notifier;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 3a0115bdcee5..a4496ee2e9b4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -10,6 +10,7 @@
 
 #include <linux/clk.h>
 #include <linux/interrupt.h>
+#include <linux/mfd/syscon.h>
 #include <linux/module.h>
 #include <linux/of.h>
 #include <linux/of_graph.h>
@@ -569,6 +570,21 @@ static int rkisp1_probe(struct platform_device *pdev)
 		return ret;
 	rkisp1->clk_size = info->clk_size;
 
+	if (info->isp_ver == IMX8MP_V10) {
+		unsigned int id;
+
+		rkisp1->gasket = syscon_regmap_lookup_by_phandle_args(dev->of_node,
+								      "fsl,blk-ctrl",
+								      1, &id);
+		if (IS_ERR(rkisp1->gasket)) {
+			ret = PTR_ERR(rkisp1->gasket);
+			dev_err(dev, "failed to get gasket: %d\n", ret);
+			return ret;
+		}
+
+		rkisp1->gasket_id = id;
+	}
+
 	pm_runtime_enable(&pdev->dev);
 
 	ret = pm_runtime_resume_and_get(&pdev->dev);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 8268331faca9..ddad36ab4389 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -10,6 +10,7 @@
 
 #include <linux/iopoll.h>
 #include <linux/pm_runtime.h>
+#include <linux/regmap.h>
 #include <linux/videodev2.h>
 #include <linux/vmalloc.h>
 
@@ -87,6 +88,115 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
 		return v4l2_subdev_get_try_crop(&isp->sd, &state, pad);
 }
 
+/* -----------------------------------------------------------------------------
+ * Media block control (i.MX8MP only)
+ */
+
+#define ISP_DEWARP_CONTROL				0x0138
+
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_HS_POLARITY	BIT(22)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_RISING	(0 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_NEGATIVE	(1 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_POSITIVE	(2 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_FALLING	(3 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_MASK	GENMASK(21, 20)
+#define ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE	BIT(19)
+#define ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE(dt)	((dt) << 13)
+#define ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE_MASK	GENMASK(18, 13)
+
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_HS_POLARITY	BIT(12)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_RISING	(0 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_NEGATIVE	(1 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_POSITIVE	(2 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_FALLING	(3 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_MASK	GENMASK(11, 10)
+#define ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE	BIT(9)
+#define ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE(dt)	((dt) << 3)
+#define ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE_MASK	GENMASK(8, 3)
+
+#define ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE		BIT(1)
+#define ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE		BIT(0)
+
+static int rkisp1_gasket_enable(struct rkisp1_device *rkisp1,
+				struct media_pad *source)
+{
+	struct v4l2_subdev *source_sd;
+	struct v4l2_mbus_frame_desc fd;
+	unsigned int dt;
+	u32 mask;
+	u32 val;
+	int ret;
+
+	/*
+	 * Configure and enable the gasket with the CSI-2 data type. Set the
+	 * vsync polarity as active high, as that is what the ISP is configured
+	 * to expect in ISP_ACQ_PROP. Enable left justification, as the i.MX8MP
+	 * ISP has a 16-bit wide input and expects data to be left-aligned.
+	 */
+
+	source_sd = media_entity_to_v4l2_subdev(source->entity);
+	ret = v4l2_subdev_call(source_sd, pad, get_frame_desc,
+			       source->index, &fd);
+	if (ret) {
+		dev_err(rkisp1->dev,
+			"failed to get frame descriptor from '%s':%u: %d\n",
+			source_sd->name, 0, ret);
+		return ret;
+	}
+
+	if (fd.num_entries != 1) {
+		dev_err(rkisp1->dev, "invalid frame descriptor for '%s':%u\n",
+			source_sd->name, 0);
+		return -EINVAL;
+	}
+
+	dt = fd.entry[0].bus.csi2.dt;
+
+	if (rkisp1->gasket_id == 0) {
+		mask = ISP_DEWARP_CONTROL_MIPI_CSI1_HS_POLARITY
+		     | ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_MASK
+		     | ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE;
+		val = ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_POSITIVE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE(dt);
+	} else {
+		mask = ISP_DEWARP_CONTROL_MIPI_CSI2_HS_POLARITY
+		     | ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_MASK
+		     | ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE;
+		val = ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_POSITIVE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE(dt);
+	}
+
+	regmap_update_bits(rkisp1->gasket, ISP_DEWARP_CONTROL, mask, val);
+
+	return 0;
+}
+
+static void rkisp1_gasket_disable(struct rkisp1_device *rkisp1)
+{
+	u32 mask;
+	u32 val;
+
+	if (rkisp1->gasket_id == 1) {
+		mask = ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE;
+		val = ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE;
+	} else {
+		mask = ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE;
+		val = ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE;
+	}
+
+	regmap_update_bits(rkisp1->gasket, ISP_DEWARP_CONTROL, mask, val);
+}
+
 /* ----------------------------------------------------------------------------
  * Camera Interface registers configurations
  */
@@ -303,6 +413,9 @@ static void rkisp1_isp_stop(struct rkisp1_isp *isp)
 		     RKISP1_CIF_VI_IRCL_MIPI_SW_RST |
 		     RKISP1_CIF_VI_IRCL_ISP_SW_RST);
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_IRCL, 0x0);
+
+	if (rkisp1->info->isp_ver == IMX8MP_V10)
+		rkisp1_gasket_disable(rkisp1);
 }
 
 static void rkisp1_config_clk(struct rkisp1_isp *isp)
@@ -327,19 +440,28 @@ static void rkisp1_config_clk(struct rkisp1_isp *isp)
 	}
 }
 
-static void rkisp1_isp_start(struct rkisp1_isp *isp)
+static int rkisp1_isp_start(struct rkisp1_isp *isp, struct media_pad *source)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
+	int ret;
 
 	rkisp1_config_clk(isp);
 
+	if (rkisp1->info->isp_ver == IMX8MP_V10) {
+		ret = rkisp1_gasket_enable(rkisp1, source);
+		if (ret)
+			return ret;
+	}
+
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
 	       RKISP1_CIF_ISP_CTRL_ISP_ENABLE |
 	       RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE;
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, val);
+
+	return 0;
 }
 
 /* ----------------------------------------------------------------------------
@@ -770,7 +892,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (ret)
 		goto mutex_unlock;
 
-	rkisp1_isp_start(isp);
+	ret = rkisp1_isp_start(isp, source_pad);
+	if (ret)
+		goto mutex_unlock;
 
 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 49/55] media: rkisp1: Configure gasket on i.MX8MP
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

The i.MX8MP has a gasket between the CSI-2 receiver and the ISP.
Configure and enable it when starting the ISP, and disable it when
stopping.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |   5 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  16 +++
 .../platform/rockchip/rkisp1/rkisp1-isp.c     | 128 +++++++++++++++++-
 3 files changed, 147 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index eccdd3f9bc89..667fca0fef95 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -24,6 +24,7 @@
 #include "rkisp1-regs.h"
 
 struct dentry;
+struct regmap;
 
 /*
  * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
@@ -451,6 +452,8 @@ struct rkisp1_debug {
  * @dev:	   a pointer to the struct device
  * @clk_size:	   number of clocks
  * @clks:	   array of clocks
+ * @gasket:	   the gasket - i.MX8MP only
+ * @gasket_id:	   the gasket ID (0 or 1) - i.MX8MP only
  * @v4l2_dev:	   v4l2_device variable
  * @media_dev:	   media_device variable
  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
@@ -471,6 +474,8 @@ struct rkisp1_device {
 	struct device *dev;
 	unsigned int clk_size;
 	struct clk_bulk_data clks[RKISP1_MAX_BUS_CLK];
+	struct regmap *gasket;
+	unsigned int gasket_id;
 	struct v4l2_device v4l2_dev;
 	struct media_device media_dev;
 	struct v4l2_async_notifier notifier;
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 3a0115bdcee5..a4496ee2e9b4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -10,6 +10,7 @@
 
 #include <linux/clk.h>
 #include <linux/interrupt.h>
+#include <linux/mfd/syscon.h>
 #include <linux/module.h>
 #include <linux/of.h>
 #include <linux/of_graph.h>
@@ -569,6 +570,21 @@ static int rkisp1_probe(struct platform_device *pdev)
 		return ret;
 	rkisp1->clk_size = info->clk_size;
 
+	if (info->isp_ver == IMX8MP_V10) {
+		unsigned int id;
+
+		rkisp1->gasket = syscon_regmap_lookup_by_phandle_args(dev->of_node,
+								      "fsl,blk-ctrl",
+								      1, &id);
+		if (IS_ERR(rkisp1->gasket)) {
+			ret = PTR_ERR(rkisp1->gasket);
+			dev_err(dev, "failed to get gasket: %d\n", ret);
+			return ret;
+		}
+
+		rkisp1->gasket_id = id;
+	}
+
 	pm_runtime_enable(&pdev->dev);
 
 	ret = pm_runtime_resume_and_get(&pdev->dev);
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
index 8268331faca9..ddad36ab4389 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
@@ -10,6 +10,7 @@
 
 #include <linux/iopoll.h>
 #include <linux/pm_runtime.h>
+#include <linux/regmap.h>
 #include <linux/videodev2.h>
 #include <linux/vmalloc.h>
 
@@ -87,6 +88,115 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
 		return v4l2_subdev_get_try_crop(&isp->sd, &state, pad);
 }
 
+/* -----------------------------------------------------------------------------
+ * Media block control (i.MX8MP only)
+ */
+
+#define ISP_DEWARP_CONTROL				0x0138
+
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_HS_POLARITY	BIT(22)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_RISING	(0 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_NEGATIVE	(1 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_POSITIVE	(2 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_FALLING	(3 << 20)
+#define ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_MASK	GENMASK(21, 20)
+#define ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE	BIT(19)
+#define ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE(dt)	((dt) << 13)
+#define ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE_MASK	GENMASK(18, 13)
+
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_HS_POLARITY	BIT(12)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_RISING	(0 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_NEGATIVE	(1 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_POSITIVE	(2 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_FALLING	(3 << 10)
+#define ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_MASK	GENMASK(11, 10)
+#define ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE	BIT(9)
+#define ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE(dt)	((dt) << 3)
+#define ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE_MASK	GENMASK(8, 3)
+
+#define ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE		BIT(1)
+#define ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE		BIT(0)
+
+static int rkisp1_gasket_enable(struct rkisp1_device *rkisp1,
+				struct media_pad *source)
+{
+	struct v4l2_subdev *source_sd;
+	struct v4l2_mbus_frame_desc fd;
+	unsigned int dt;
+	u32 mask;
+	u32 val;
+	int ret;
+
+	/*
+	 * Configure and enable the gasket with the CSI-2 data type. Set the
+	 * vsync polarity as active high, as that is what the ISP is configured
+	 * to expect in ISP_ACQ_PROP. Enable left justification, as the i.MX8MP
+	 * ISP has a 16-bit wide input and expects data to be left-aligned.
+	 */
+
+	source_sd = media_entity_to_v4l2_subdev(source->entity);
+	ret = v4l2_subdev_call(source_sd, pad, get_frame_desc,
+			       source->index, &fd);
+	if (ret) {
+		dev_err(rkisp1->dev,
+			"failed to get frame descriptor from '%s':%u: %d\n",
+			source_sd->name, 0, ret);
+		return ret;
+	}
+
+	if (fd.num_entries != 1) {
+		dev_err(rkisp1->dev, "invalid frame descriptor for '%s':%u\n",
+			source_sd->name, 0);
+		return -EINVAL;
+	}
+
+	dt = fd.entry[0].bus.csi2.dt;
+
+	if (rkisp1->gasket_id == 0) {
+		mask = ISP_DEWARP_CONTROL_MIPI_CSI1_HS_POLARITY
+		     | ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_MASK
+		     | ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE;
+		val = ISP_DEWARP_CONTROL_MIPI_CSI1_VS_SEL_POSITIVE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE(dt);
+	} else {
+		mask = ISP_DEWARP_CONTROL_MIPI_CSI2_HS_POLARITY
+		     | ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_MASK
+		     | ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE;
+		val = ISP_DEWARP_CONTROL_MIPI_CSI2_VS_SEL_POSITIVE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE
+		    | ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE(dt);
+	}
+
+	regmap_update_bits(rkisp1->gasket, ISP_DEWARP_CONTROL, mask, val);
+
+	return 0;
+}
+
+static void rkisp1_gasket_disable(struct rkisp1_device *rkisp1)
+{
+	u32 mask;
+	u32 val;
+
+	if (rkisp1->gasket_id == 1) {
+		mask = ISP_DEWARP_CONTROL_MIPI_ISP2_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP2_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE;
+		val = ISP_DEWARP_CONTROL_GPR_ISP_1_DISABLE;
+	} else {
+		mask = ISP_DEWARP_CONTROL_MIPI_ISP1_LEFT_JUST_MODE
+		     | ISP_DEWARP_CONTROL_MIPI_ISP1_DATA_TYPE_MASK
+		     | ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE;
+		val = ISP_DEWARP_CONTROL_GPR_ISP_0_DISABLE;
+	}
+
+	regmap_update_bits(rkisp1->gasket, ISP_DEWARP_CONTROL, mask, val);
+}
+
 /* ----------------------------------------------------------------------------
  * Camera Interface registers configurations
  */
@@ -303,6 +413,9 @@ static void rkisp1_isp_stop(struct rkisp1_isp *isp)
 		     RKISP1_CIF_VI_IRCL_MIPI_SW_RST |
 		     RKISP1_CIF_VI_IRCL_ISP_SW_RST);
 	rkisp1_write(rkisp1, RKISP1_CIF_VI_IRCL, 0x0);
+
+	if (rkisp1->info->isp_ver == IMX8MP_V10)
+		rkisp1_gasket_disable(rkisp1);
 }
 
 static void rkisp1_config_clk(struct rkisp1_isp *isp)
@@ -327,19 +440,28 @@ static void rkisp1_config_clk(struct rkisp1_isp *isp)
 	}
 }
 
-static void rkisp1_isp_start(struct rkisp1_isp *isp)
+static int rkisp1_isp_start(struct rkisp1_isp *isp, struct media_pad *source)
 {
 	struct rkisp1_device *rkisp1 = isp->rkisp1;
 	u32 val;
+	int ret;
 
 	rkisp1_config_clk(isp);
 
+	if (rkisp1->info->isp_ver == IMX8MP_V10) {
+		ret = rkisp1_gasket_enable(rkisp1, source);
+		if (ret)
+			return ret;
+	}
+
 	/* Activate ISP */
 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
 	       RKISP1_CIF_ISP_CTRL_ISP_ENABLE |
 	       RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE;
 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, val);
+
+	return 0;
 }
 
 /* ----------------------------------------------------------------------------
@@ -770,7 +892,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
 	if (ret)
 		goto mutex_unlock;
 
-	rkisp1_isp_start(isp);
+	ret = rkisp1_isp_start(isp, source_pad);
+	if (ret)
+		goto mutex_unlock;
 
 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
 	if (ret) {
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP version in the i.MX8MP has a separate set of registers for crop
that is currently not handled. Add a feature flag to determine which
type of crop the ISP supports and set the crop registers based on that.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
 .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
 .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
 .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
 5 files changed, 46 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 667fca0fef95..e4f422bed09a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
  */
 enum rkisp1_feature {
 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
+	RKISP1_FEATURE_DUAL_CROP = BIT(1),
+	RKISP1_FEATURE_RSZ_CROP = BIT(2),
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
index 02854e8ea1a4..753abd024ce7 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
@@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
 		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
 		{ /* Sentinel */ },
 	};
+	static const struct rkisp1_debug_register crop_registers[] = {
+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
+		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
+		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
+		{ /* Sentinel */ },
+	};
 	struct rkisp1_resizer *rsz = m->private;
 
-	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
+	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
+		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
+				       crop_registers);
+
+	return 0;
 }
 DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index a4496ee2e9b4..5abe33f5fed4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
 	.isrs = px30_isp_isrs,
 	.isr_size = ARRAY_SIZE(px30_isp_isrs),
 	.isp_ver = RKISP1_V12,
-	.features = RKISP1_FEATURE_MIPI_CSI2,
+	.features = RKISP1_FEATURE_MIPI_CSI2
+		  | RKISP1_FEATURE_DUAL_CROP,
 };
 
 static const char * const rk3399_isp_clks[] = {
@@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
 	.isrs = rk3399_isp_isrs,
 	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
 	.isp_ver = RKISP1_V10,
-	.features = RKISP1_FEATURE_MIPI_CSI2,
+	.features = RKISP1_FEATURE_MIPI_CSI2
+		  | RKISP1_FEATURE_DUAL_CROP,
 };
 
 static const char * const imx8mp_isp_clks[] = {
@@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
 	.isrs = imx8mp_isp_isrs,
 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
 	.isp_ver = IMX8MP_V10,
+	.features = RKISP1_FEATURE_RSZ_CROP,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index dd3e6c38be67..1fc54ab22b6d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -168,6 +168,9 @@
 #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
 #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
 
+/* RSZ_CROP_[XY]_DIR */
+#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
+
 /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
 #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
 #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
@@ -926,6 +929,12 @@
 #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
 #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
 #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
+#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
+#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
+#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
+#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
+#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
 
 #define RKISP1_CIF_MI_BASE			0x00001400
 #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
index f4caa8f684aa..08bf3aa8088f 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
@@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
 {
 	u32 ratio, rsz_ctrl = 0;
 	unsigned int i;
+	u32 val;
 
 	/* No phase offset */
 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
@@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
 
 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
 
+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
+
+		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;
+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
+	}
+
 	rkisp1_rsz_update_shadow(rsz, when);
 }
 
@@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
 	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
 
 	if (!enable) {
-		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
+		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
+			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
 		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
 		return 0;
 	}
@@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
 
 	mutex_lock(&rsz->ops_lock);
 	rkisp1_rsz_config(rsz, when);
-	rkisp1_dcrop_config(rsz);
+	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
+		rkisp1_dcrop_config(rsz);
 
 	mutex_unlock(&rsz->ops_lock);
 	return 0;
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP version in the i.MX8MP has a separate set of registers for crop
that is currently not handled. Add a feature flag to determine which
type of crop the ISP supports and set the crop registers based on that.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
 .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
 .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
 .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
 5 files changed, 46 insertions(+), 5 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 667fca0fef95..e4f422bed09a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
  */
 enum rkisp1_feature {
 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
+	RKISP1_FEATURE_DUAL_CROP = BIT(1),
+	RKISP1_FEATURE_RSZ_CROP = BIT(2),
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
index 02854e8ea1a4..753abd024ce7 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
@@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
 		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
 		{ /* Sentinel */ },
 	};
+	static const struct rkisp1_debug_register crop_registers[] = {
+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
+		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
+		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
+		{ /* Sentinel */ },
+	};
 	struct rkisp1_resizer *rsz = m->private;
 
-	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
+	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
+		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
+				       crop_registers);
+
+	return 0;
 }
 DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index a4496ee2e9b4..5abe33f5fed4 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
 	.isrs = px30_isp_isrs,
 	.isr_size = ARRAY_SIZE(px30_isp_isrs),
 	.isp_ver = RKISP1_V12,
-	.features = RKISP1_FEATURE_MIPI_CSI2,
+	.features = RKISP1_FEATURE_MIPI_CSI2
+		  | RKISP1_FEATURE_DUAL_CROP,
 };
 
 static const char * const rk3399_isp_clks[] = {
@@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
 	.isrs = rk3399_isp_isrs,
 	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
 	.isp_ver = RKISP1_V10,
-	.features = RKISP1_FEATURE_MIPI_CSI2,
+	.features = RKISP1_FEATURE_MIPI_CSI2
+		  | RKISP1_FEATURE_DUAL_CROP,
 };
 
 static const char * const imx8mp_isp_clks[] = {
@@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
 	.isrs = imx8mp_isp_isrs,
 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
 	.isp_ver = IMX8MP_V10,
+	.features = RKISP1_FEATURE_RSZ_CROP,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index dd3e6c38be67..1fc54ab22b6d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -168,6 +168,9 @@
 #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
 #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
 
+/* RSZ_CROP_[XY]_DIR */
+#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
+
 /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
 #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
 #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
@@ -926,6 +929,12 @@
 #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
 #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
 #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
+#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
+#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
+#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
+#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
+#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
 
 #define RKISP1_CIF_MI_BASE			0x00001400
 #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
index f4caa8f684aa..08bf3aa8088f 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
@@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
 {
 	u32 ratio, rsz_ctrl = 0;
 	unsigned int i;
+	u32 val;
 
 	/* No phase offset */
 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
@@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
 
 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
 
+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
+
+		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;
+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
+	}
+
 	rkisp1_rsz_update_shadow(rsz, when);
 }
 
@@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
 	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
 
 	if (!enable) {
-		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
+		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
+			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
 		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
 		return 0;
 	}
@@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
 
 	mutex_lock(&rsz->ops_lock);
 	rkisp1_rsz_config(rsz, when);
-	rkisp1_dcrop_config(rsz);
+	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
+		rkisp1_dcrop_config(rsz);
 
 	mutex_unlock(&rsz->ops_lock);
 	return 0;
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP version in the i.MX8MP has a set of registers currently not
handled by the driver for output size configuration. Add a feature flag
to determine if the ISP requires this, and set the registers based on
that.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c | 8 ++++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-common.h  | 1 +
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c     | 3 ++-
 drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h    | 9 +++++++++
 4 files changed, 20 insertions(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 9edaa95fa44c..35cec263c563 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -420,6 +420,14 @@ static void rkisp1_mp_config(struct rkisp1_capture *cap)
 	rkisp1_write(rkisp1, cap->config->mi.cr_size_init,
 		     rkisp1_pixfmt_comp_size(pixm, RKISP1_PLANE_CR));
 
+	if (rkisp1->info->features & RKISP1_FEATURE_MAIN_STRIDE) {
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_LLENGTH, pixm->width);
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_WIDTH, pixm->width);
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_HEIGHT, pixm->height);
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_SIZE,
+			     pixm->width * pixm->height);
+	}
+
 	rkisp1_irq_frame_end_enable(cap);
 
 	/* set uv swapping for semiplanar formats */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index e4f422bed09a..96657e55a5b0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -112,6 +112,7 @@ enum rkisp1_feature {
 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
 	RKISP1_FEATURE_DUAL_CROP = BIT(1),
 	RKISP1_FEATURE_RSZ_CROP = BIT(2),
+	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 5abe33f5fed4..d68a805e8b6b 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -505,7 +505,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
 	.isrs = imx8mp_isp_isrs,
 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
 	.isp_ver = IMX8MP_V10,
-	.features = RKISP1_FEATURE_RSZ_CROP,
+	.features = RKISP1_FEATURE_RSZ_CROP
+		  | RKISP1_FEATURE_MAIN_STRIDE,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index 1fc54ab22b6d..5c2195019723 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -1013,6 +1013,15 @@
 #define RKISP1_CIF_MI_SP_CB_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000140)
 #define RKISP1_CIF_MI_SP_CR_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000144)
 #define RKISP1_CIF_MI_XTD_FORMAT_CTRL		(RKISP1_CIF_MI_BASE + 0x00000148)
+#define RKISP1_CIF_MI_MP_HANDSHAKE_0		(RKISP1_CIF_MI_BASE + 0x0000014C)
+#define RKISP1_CIF_MI_MP_Y_LLENGTH		(RKISP1_CIF_MI_BASE + 0x00000150)
+#define RKISP1_CIF_MI_MP_Y_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000154)
+#define RKISP1_CIF_MI_MP_C_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000158)
+#define RKISP1_CIF_MI_OUTPUT_ALIGN_FORMAT	(RKISP1_CIF_MI_BASE + 0x0000015C)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE	(RKISP1_CIF_MI_BASE + 0x00000160)
+#define RKISP1_CIF_MI_MP_Y_PIC_WIDTH		(RKISP1_CIF_MI_BASE + 0x00000164)
+#define RKISP1_CIF_MI_MP_Y_PIC_HEIGHT		(RKISP1_CIF_MI_BASE + 0x00000168)
+#define RKISP1_CIF_MI_MP_Y_PIC_SIZE		(RKISP1_CIF_MI_BASE + 0x0000016C)
 
 #define RKISP1_CIF_SMIA_BASE			0x00001A00
 #define RKISP1_CIF_SMIA_CTRL			(RKISP1_CIF_SMIA_BASE + 0x00000000)
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP version in the i.MX8MP has a set of registers currently not
handled by the driver for output size configuration. Add a feature flag
to determine if the ISP requires this, and set the registers based on
that.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c | 8 ++++++++
 drivers/media/platform/rockchip/rkisp1/rkisp1-common.h  | 1 +
 drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c     | 3 ++-
 drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h    | 9 +++++++++
 4 files changed, 20 insertions(+), 1 deletion(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 9edaa95fa44c..35cec263c563 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -420,6 +420,14 @@ static void rkisp1_mp_config(struct rkisp1_capture *cap)
 	rkisp1_write(rkisp1, cap->config->mi.cr_size_init,
 		     rkisp1_pixfmt_comp_size(pixm, RKISP1_PLANE_CR));
 
+	if (rkisp1->info->features & RKISP1_FEATURE_MAIN_STRIDE) {
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_LLENGTH, pixm->width);
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_WIDTH, pixm->width);
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_HEIGHT, pixm->height);
+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_SIZE,
+			     pixm->width * pixm->height);
+	}
+
 	rkisp1_irq_frame_end_enable(cap);
 
 	/* set uv swapping for semiplanar formats */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index e4f422bed09a..96657e55a5b0 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -112,6 +112,7 @@ enum rkisp1_feature {
 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
 	RKISP1_FEATURE_DUAL_CROP = BIT(1),
 	RKISP1_FEATURE_RSZ_CROP = BIT(2),
+	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index 5abe33f5fed4..d68a805e8b6b 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -505,7 +505,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
 	.isrs = imx8mp_isp_isrs,
 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
 	.isp_ver = IMX8MP_V10,
-	.features = RKISP1_FEATURE_RSZ_CROP,
+	.features = RKISP1_FEATURE_RSZ_CROP
+		  | RKISP1_FEATURE_MAIN_STRIDE,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index 1fc54ab22b6d..5c2195019723 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -1013,6 +1013,15 @@
 #define RKISP1_CIF_MI_SP_CB_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000140)
 #define RKISP1_CIF_MI_SP_CR_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000144)
 #define RKISP1_CIF_MI_XTD_FORMAT_CTRL		(RKISP1_CIF_MI_BASE + 0x00000148)
+#define RKISP1_CIF_MI_MP_HANDSHAKE_0		(RKISP1_CIF_MI_BASE + 0x0000014C)
+#define RKISP1_CIF_MI_MP_Y_LLENGTH		(RKISP1_CIF_MI_BASE + 0x00000150)
+#define RKISP1_CIF_MI_MP_Y_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000154)
+#define RKISP1_CIF_MI_MP_C_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000158)
+#define RKISP1_CIF_MI_OUTPUT_ALIGN_FORMAT	(RKISP1_CIF_MI_BASE + 0x0000015C)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE	(RKISP1_CIF_MI_BASE + 0x00000160)
+#define RKISP1_CIF_MI_MP_Y_PIC_WIDTH		(RKISP1_CIF_MI_BASE + 0x00000164)
+#define RKISP1_CIF_MI_MP_Y_PIC_HEIGHT		(RKISP1_CIF_MI_BASE + 0x00000168)
+#define RKISP1_CIF_MI_MP_Y_PIC_SIZE		(RKISP1_CIF_MI_BASE + 0x0000016C)
 
 #define RKISP1_CIF_SMIA_BASE			0x00001A00
 #define RKISP1_CIF_SMIA_CTRL			(RKISP1_CIF_SMIA_BASE + 0x00000000)
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 52/55] media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add register definitions for resizer format conversion control and for
the memory interface output that are specific to the ISP version in the
i.MX8MP.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-regs.h    | 33 +++++++++++++++++++
 1 file changed, 33 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index 5c2195019723..dd63ae13e603 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -171,6 +171,23 @@
 /* RSZ_CROP_[XY]_DIR */
 #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
 
+/* RSZ_FORMAT_CONV_CTRL */
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_400	(0 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_420	(1 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422	(2 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_444	(3 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_400	(0 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420	(1 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_422	(2 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_444	(3 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_Y_FULL			BIT(5)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_CBCR_FULL			BIT(6)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_422NOCOSITED		BIT(7)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_ENABLE	BIT(8)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_METHOD	BIT(9)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_PLANAR		(0 << 10)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR	(1 << 10)
+
 /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
 #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
 #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
@@ -212,6 +229,22 @@
 #define RKISP1_CIF_MI_XTD_FMT_CTRL_MP_CB_CR_SWAP	BIT(0)
 #define RKISP1_CIF_MI_XTD_FMT_CTRL_SP_CB_CR_SWAP	BIT(1)
 #define RKISP1_CIF_MI_XTD_FMT_CTRL_DMA_CB_CR_SWAP	BIT(2)
+/* MI_OUTPUT_ALIGN_FORMAT */
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_LSB_ALIGNMENT			BIT(0)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_BYTES		BIT(1)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_WORDS		BIT(2)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_DWORDS		BIT(3)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_BYTES		BIT(4)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_WORDS		BIT(5)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_DWORDS		BIT(6)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_BYTES		BIT(7)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_WORDS		BIT(8)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_DWORDS		BIT(9)
+/* MI_MP_OUTPUT_FIFO_SIZE */
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_FULL	(0 << 0)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_HALF	(1 << 0)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_QUARTER	(2 << 0)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_EIGHT	(3 << 0)
 
 /* VI_CCL */
 #define RKISP1_CIF_CCL_CIF_CLK_DIS			BIT(2)
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 52/55] media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add register definitions for resizer format conversion control and for
the memory interface output that are specific to the ISP version in the
i.MX8MP.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-regs.h    | 33 +++++++++++++++++++
 1 file changed, 33 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index 5c2195019723..dd63ae13e603 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -171,6 +171,23 @@
 /* RSZ_CROP_[XY]_DIR */
 #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
 
+/* RSZ_FORMAT_CONV_CTRL */
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_400	(0 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_420	(1 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422	(2 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_444	(3 << 0)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_400	(0 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420	(1 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_422	(2 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_444	(3 << 2)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_Y_FULL			BIT(5)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_CBCR_FULL			BIT(6)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_422NOCOSITED		BIT(7)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_ENABLE	BIT(8)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_METHOD	BIT(9)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_PLANAR		(0 << 10)
+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR	(1 << 10)
+
 /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
 #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
 #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
@@ -212,6 +229,22 @@
 #define RKISP1_CIF_MI_XTD_FMT_CTRL_MP_CB_CR_SWAP	BIT(0)
 #define RKISP1_CIF_MI_XTD_FMT_CTRL_SP_CB_CR_SWAP	BIT(1)
 #define RKISP1_CIF_MI_XTD_FMT_CTRL_DMA_CB_CR_SWAP	BIT(2)
+/* MI_OUTPUT_ALIGN_FORMAT */
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_LSB_ALIGNMENT			BIT(0)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_BYTES		BIT(1)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_WORDS		BIT(2)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_DWORDS		BIT(3)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_BYTES		BIT(4)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_WORDS		BIT(5)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_DWORDS		BIT(6)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_BYTES		BIT(7)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_WORDS		BIT(8)
+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_DWORDS		BIT(9)
+/* MI_MP_OUTPUT_FIFO_SIZE */
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_FULL	(0 << 0)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_HALF	(1 << 0)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_QUARTER	(2 << 0)
+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_EIGHT	(3 << 0)
 
 /* VI_CCL */
 #define RKISP1_CIF_CCL_CIF_CLK_DIS			BIT(2)
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
encoded in 34-bit. Shift them to the left by 2 bits so that they can be
contained in 32 bits.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
 3 files changed, 14 insertions(+), 9 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 35cec263c563..234b1f8488cb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
 
 static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 {
+	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
+		   2 : 0;
+
 	cap->buf.curr = cap->buf.next;
 	cap->buf.next = NULL;
 
@@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 		buff_addr = cap->buf.next->buff_addr;
 
 		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
-			     buff_addr[RKISP1_PLANE_Y]);
+			     buff_addr[RKISP1_PLANE_Y] >> shift);
 		/*
 		 * In order to support grey format we capture
 		 * YUV422 planar format from the camera and
@@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cb_base_ad_init,
-				     cap->buf.dummy.dma_addr);
+				     cap->buf.dummy.dma_addr >> shift);
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cr_base_ad_init,
-				     cap->buf.dummy.dma_addr);
+				     cap->buf.dummy.dma_addr >> shift);
 		} else {
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cb_base_ad_init,
-				     buff_addr[RKISP1_PLANE_CB]);
+				     buff_addr[RKISP1_PLANE_CB] >> shift);
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cr_base_ad_init,
-				     buff_addr[RKISP1_PLANE_CR]);
+				     buff_addr[RKISP1_PLANE_CR] >> shift);
 		}
 	} else {
 		/*
@@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 		 * throw data if there is no available buffer.
 		 */
 		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
-			     cap->buf.dummy.dma_addr);
+			     cap->buf.dummy.dma_addr >> shift);
 		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
-			     cap->buf.dummy.dma_addr);
+			     cap->buf.dummy.dma_addr >> shift);
 		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
-			     cap->buf.dummy.dma_addr);
+			     cap->buf.dummy.dma_addr >> shift);
 	}
 
 	/* Set plane offsets */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 96657e55a5b0..0b834579d08c 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -113,6 +113,7 @@ enum rkisp1_feature {
 	RKISP1_FEATURE_DUAL_CROP = BIT(1),
 	RKISP1_FEATURE_RSZ_CROP = BIT(2),
 	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
+	RKISP1_FEATURE_DMA_34BIT = BIT(4),
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index d68a805e8b6b..4c77aa2bc50a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
 	.isp_ver = IMX8MP_V10,
 	.features = RKISP1_FEATURE_RSZ_CROP
-		  | RKISP1_FEATURE_MAIN_STRIDE,
+		  | RKISP1_FEATURE_MAIN_STRIDE
+		  | RKISP1_FEATURE_DMA_34BIT,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
encoded in 34-bit. Shift them to the left by 2 bits so that they can be
contained in 32 bits.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
 .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
 .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
 3 files changed, 14 insertions(+), 9 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
index 35cec263c563..234b1f8488cb 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
@@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
 
 static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 {
+	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
+		   2 : 0;
+
 	cap->buf.curr = cap->buf.next;
 	cap->buf.next = NULL;
 
@@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 		buff_addr = cap->buf.next->buff_addr;
 
 		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
-			     buff_addr[RKISP1_PLANE_Y]);
+			     buff_addr[RKISP1_PLANE_Y] >> shift);
 		/*
 		 * In order to support grey format we capture
 		 * YUV422 planar format from the camera and
@@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cb_base_ad_init,
-				     cap->buf.dummy.dma_addr);
+				     cap->buf.dummy.dma_addr >> shift);
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cr_base_ad_init,
-				     cap->buf.dummy.dma_addr);
+				     cap->buf.dummy.dma_addr >> shift);
 		} else {
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cb_base_ad_init,
-				     buff_addr[RKISP1_PLANE_CB]);
+				     buff_addr[RKISP1_PLANE_CB] >> shift);
 			rkisp1_write(cap->rkisp1,
 				     cap->config->mi.cr_base_ad_init,
-				     buff_addr[RKISP1_PLANE_CR]);
+				     buff_addr[RKISP1_PLANE_CR] >> shift);
 		}
 	} else {
 		/*
@@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
 		 * throw data if there is no available buffer.
 		 */
 		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
-			     cap->buf.dummy.dma_addr);
+			     cap->buf.dummy.dma_addr >> shift);
 		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
-			     cap->buf.dummy.dma_addr);
+			     cap->buf.dummy.dma_addr >> shift);
 		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
-			     cap->buf.dummy.dma_addr);
+			     cap->buf.dummy.dma_addr >> shift);
 	}
 
 	/* Set plane offsets */
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
index 96657e55a5b0..0b834579d08c 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
@@ -113,6 +113,7 @@ enum rkisp1_feature {
 	RKISP1_FEATURE_DUAL_CROP = BIT(1),
 	RKISP1_FEATURE_RSZ_CROP = BIT(2),
 	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
+	RKISP1_FEATURE_DMA_34BIT = BIT(4),
 };
 
 /*
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
index d68a805e8b6b..4c77aa2bc50a 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
@@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
 	.isp_ver = IMX8MP_V10,
 	.features = RKISP1_FEATURE_RSZ_CROP
-		  | RKISP1_FEATURE_MAIN_STRIDE,
+		  | RKISP1_FEATURE_MAIN_STRIDE
+		  | RKISP1_FEATURE_DMA_34BIT,
 };
 
 static const struct of_device_id rkisp1_of_match[] = {
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 54/55] media: rkisp1: Add register definitions for the test pattern generator
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add register definitions and value macros for the test pattern generator
block in the ISP.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-regs.h    | 32 +++++++++++++++++++
 1 file changed, 32 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index dd63ae13e603..34f4fe09c88d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -717,6 +717,27 @@
 #define RKISP1_CIF_ISP_DPF_SPATIAL_COEFF_MAX		0x1F
 #define RKISP1_CIF_ISP_DPF_NLL_COEFF_N_MAX		0x3FF
 
+/* TPG */
+#define RKISP1_CIF_ISP_TPG_CTRL_ENA			BIT(0)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_3X3_COLOR_BLOCK	(0 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_COLOR_BAR		(1 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_GRAY_BAR		(2 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_HIGHLIGHT_GRID	(3 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_RAND		(4 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_RGGB		(0 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_GRBG		(1 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_GBRB		(2 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_BGGR		(3 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEPTH_8			(0 << 6)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEPTH_10		(1 << 6)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEPTH_12		(2 << 6)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEF_SYNC		BIT(8)
+#define RKISP1_CIF_ISP_TPG_CTRL_MAX_SYNC		BIT(9)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_1080P		(0 << 10)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_720P		(1 << 10)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_4K			(2 << 10)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_USER_DEFINED	(3 << 10)
+
 /* =================================================================== */
 /*                            CIF Registers                            */
 /* =================================================================== */
@@ -912,6 +933,17 @@
 #define RKISP1_CIF_ISP_SH_DELAY			(RKISP1_CIF_ISP_SH_BASE + 0x00000008)
 #define RKISP1_CIF_ISP_SH_TIME			(RKISP1_CIF_ISP_SH_BASE + 0x0000000C)
 
+#define RKISP1_CIF_ISP_TPG_BASE			0x00000700
+#define RKISP1_CIF_ISP_TPG_CTRL			(RKISP1_CIF_ISP_TPG_BASE + 0x00000000)
+#define RKISP1_CIF_ISP_TPG_TOTAL_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000004)
+#define RKISP1_CIF_ISP_TPG_ACT_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000008)
+#define RKISP1_CIF_ISP_TPG_FP_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x0000000C)
+#define RKISP1_CIF_ISP_TPG_BP_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000010)
+#define RKISP1_CIF_ISP_TPG_W_IN			(RKISP1_CIF_ISP_TPG_BASE + 0x00000014)
+#define RKISP1_CIF_ISP_TPG_GAP_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000018)
+#define RKISP1_CIF_ISP_TPG_GAP_STD_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x0000001C)
+#define RKISP1_CIF_ISP_TPG_RANDOM_SEED_IN	(RKISP1_CIF_ISP_TPG_BASE + 0x00000020)
+
 #define RKISP1_CIF_C_PROC_BASE			0x00000800
 #define RKISP1_CIF_C_PROC_CTRL			(RKISP1_CIF_C_PROC_BASE + 0x00000000)
 #define RKISP1_CIF_C_PROC_CONTRAST		(RKISP1_CIF_C_PROC_BASE + 0x00000004)
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 54/55] media: rkisp1: Add register definitions for the test pattern generator
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Add register definitions and value macros for the test pattern generator
block in the ISP.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 .../platform/rockchip/rkisp1/rkisp1-regs.h    | 32 +++++++++++++++++++
 1 file changed, 32 insertions(+)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index dd63ae13e603..34f4fe09c88d 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -717,6 +717,27 @@
 #define RKISP1_CIF_ISP_DPF_SPATIAL_COEFF_MAX		0x1F
 #define RKISP1_CIF_ISP_DPF_NLL_COEFF_N_MAX		0x3FF
 
+/* TPG */
+#define RKISP1_CIF_ISP_TPG_CTRL_ENA			BIT(0)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_3X3_COLOR_BLOCK	(0 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_COLOR_BAR		(1 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_GRAY_BAR		(2 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_HIGHLIGHT_GRID	(3 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_IMG_RAND		(4 << 1)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_RGGB		(0 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_GRBG		(1 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_GBRB		(2 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_CFA_BGGR		(3 << 4)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEPTH_8			(0 << 6)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEPTH_10		(1 << 6)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEPTH_12		(2 << 6)
+#define RKISP1_CIF_ISP_TPG_CTRL_DEF_SYNC		BIT(8)
+#define RKISP1_CIF_ISP_TPG_CTRL_MAX_SYNC		BIT(9)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_1080P		(0 << 10)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_720P		(1 << 10)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_4K			(2 << 10)
+#define RKISP1_CIF_ISP_TPG_CTRL_SOL_USER_DEFINED	(3 << 10)
+
 /* =================================================================== */
 /*                            CIF Registers                            */
 /* =================================================================== */
@@ -912,6 +933,17 @@
 #define RKISP1_CIF_ISP_SH_DELAY			(RKISP1_CIF_ISP_SH_BASE + 0x00000008)
 #define RKISP1_CIF_ISP_SH_TIME			(RKISP1_CIF_ISP_SH_BASE + 0x0000000C)
 
+#define RKISP1_CIF_ISP_TPG_BASE			0x00000700
+#define RKISP1_CIF_ISP_TPG_CTRL			(RKISP1_CIF_ISP_TPG_BASE + 0x00000000)
+#define RKISP1_CIF_ISP_TPG_TOTAL_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000004)
+#define RKISP1_CIF_ISP_TPG_ACT_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000008)
+#define RKISP1_CIF_ISP_TPG_FP_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x0000000C)
+#define RKISP1_CIF_ISP_TPG_BP_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000010)
+#define RKISP1_CIF_ISP_TPG_W_IN			(RKISP1_CIF_ISP_TPG_BASE + 0x00000014)
+#define RKISP1_CIF_ISP_TPG_GAP_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x00000018)
+#define RKISP1_CIF_ISP_TPG_GAP_STD_IN		(RKISP1_CIF_ISP_TPG_BASE + 0x0000001C)
+#define RKISP1_CIF_ISP_TPG_RANDOM_SEED_IN	(RKISP1_CIF_ISP_TPG_BASE + 0x00000020)
+
 #define RKISP1_CIF_C_PROC_BASE			0x00000800
 #define RKISP1_CIF_C_PROC_CTRL			(RKISP1_CIF_C_PROC_BASE + 0x00000000)
 #define RKISP1_CIF_C_PROC_CONTRAST		(RKISP1_CIF_C_PROC_BASE + 0x00000004)
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-14 19:11   ` Paul Elder
  -1 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP that is integrated in the i.MX8MP uses different bits in the
MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
compared to the on in the RK3399. In addition, it adds a new bit for
enabling crop. Add new definitions for these bits for i.MX8MP devices,
and update where they are set.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
 .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
 2 files changed, 12 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index 34f4fe09c88d..24ad2ccec2a3 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -168,6 +168,10 @@
 #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
 #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
 
+#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
+#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
+#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
+
 /* RSZ_CROP_[XY]_DIR */
 #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
index 08bf3aa8088f..29a31b18a082 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
@@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct rkisp1_resizer *rsz,
 	u32 ctrl_cfg = rkisp1_rsz_read(rsz, RKISP1_CIF_RSZ_CTRL);
 
 	if (when == RKISP1_SHADOW_REGS_ASYNC)
-		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
+		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
+		else
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
 	else
-		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
+		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
+		else
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
 
 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
 }
-- 
2.30.2


^ permalink raw reply related	[flat|nested] 298+ messages in thread

* [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
@ 2022-06-14 19:11   ` Paul Elder
  0 siblings, 0 replies; 298+ messages in thread
From: Paul Elder @ 2022-06-14 19:11 UTC (permalink / raw)
  To: linux-media
  Cc: Paul Elder, dafna, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

The ISP that is integrated in the i.MX8MP uses different bits in the
MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
compared to the on in the RK3399. In addition, it adds a new bit for
enabling crop. Add new definitions for these bits for i.MX8MP devices,
and update where they are set.

Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
---
 drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
 .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
 2 files changed, 12 insertions(+), 2 deletions(-)

diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
index 34f4fe09c88d..24ad2ccec2a3 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
@@ -168,6 +168,10 @@
 #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
 #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
 
+#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
+#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
+#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
+
 /* RSZ_CROP_[XY]_DIR */
 #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
 
diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
index 08bf3aa8088f..29a31b18a082 100644
--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
@@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct rkisp1_resizer *rsz,
 	u32 ctrl_cfg = rkisp1_rsz_read(rsz, RKISP1_CIF_RSZ_CTRL);
 
 	if (when == RKISP1_SHADOW_REGS_ASYNC)
-		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
+		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
+		else
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
 	else
-		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
+		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
+		else
+			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
 
 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
 }
-- 
2.30.2


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply related	[flat|nested] 298+ messages in thread

* Re: [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-15 22:36     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:36 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Sakari Ailus,
	Hans Verkuil

+ Sakari and Hans

This patch is needed by this series, but I think it could also be
reviewed and merged standalone already.

On Wed, Jun 15, 2022 at 04:10:48AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> Drivers typically extend the v4l2_async_subdev structure by embedding it
> in a driver-specific structure, to store per-subdev custom data. The
> v4l2_async_subdev instances are freed by the v4l2-async framework, which
> makes this mechanism cumbersome to use safely when custom data needs
> special treatment to be destroyed (such as freeing additional memory, or
> releasing references to kernel objects).
> 
> To ease this, add a .destroy() operation to the
> v4l2_async_notifier_operations structure. The operation is called right
> before the v4l2_async_subdev is freed, giving drivers a chance to
> destroy data if needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/v4l2-subdev.rst |  6 ++++++
>  drivers/media/v4l2-core/v4l2-async.c           | 10 ++++++++++
>  include/media/v4l2-async.h                     |  2 ++
>  3 files changed, 18 insertions(+)
> 
> diff --git a/Documentation/driver-api/media/v4l2-subdev.rst b/Documentation/driver-api/media/v4l2-subdev.rst
> index cf3b52bdbfb9..6f8d79926aa5 100644
> --- a/Documentation/driver-api/media/v4l2-subdev.rst
> +++ b/Documentation/driver-api/media/v4l2-subdev.rst
> @@ -243,6 +243,12 @@ notifier callback is called. After all subdevices have been located the
>  .complete() callback is called. When a subdevice is removed from the
>  system the .unbind() method is called. All three callbacks are optional.
>  
> +Drivers can store any type of custom data in their driver-specific
> +:c:type:`v4l2_async_subdev` wrapper. If any of that data requires special
> +handling when the structure is freed, drivers must implement the ``.destroy()``
> +notifier callback. The framework will call it right before freeing the
> +:c:type:`v4l2_async_subdev`.
> +
>  Calling subdev operations
>  ~~~~~~~~~~~~~~~~~~~~~~~~~
>  
> diff --git a/drivers/media/v4l2-core/v4l2-async.c b/drivers/media/v4l2-core/v4l2-async.c
> index c6995718237a..735dede624b8 100644
> --- a/drivers/media/v4l2-core/v4l2-async.c
> +++ b/drivers/media/v4l2-core/v4l2-async.c
> @@ -52,6 +52,15 @@ static int v4l2_async_nf_call_complete(struct v4l2_async_notifier *n)
>  	return n->ops->complete(n);
>  }
>  
> +static void v4l2_async_nf_call_destroy(struct v4l2_async_notifier *n,
> +				       struct v4l2_async_subdev *asd)
> +{
> +	if (!n->ops || !n->ops->destroy)
> +		return;
> +
> +	n->ops->destroy(asd);
> +}
> +
>  static bool match_i2c(struct v4l2_async_notifier *notifier,
>  		      struct v4l2_subdev *sd, struct v4l2_async_subdev *asd)
>  {
> @@ -626,6 +635,7 @@ static void __v4l2_async_nf_cleanup(struct v4l2_async_notifier *notifier)
>  		}
>  
>  		list_del(&asd->asd_list);
> +		v4l2_async_nf_call_destroy(notifier, asd);
>  		kfree(asd);
>  	}
>  }
> diff --git a/include/media/v4l2-async.h b/include/media/v4l2-async.h
> index 13ff3ad948f4..25eb1d138c06 100644
> --- a/include/media/v4l2-async.h
> +++ b/include/media/v4l2-async.h
> @@ -81,6 +81,7 @@ struct v4l2_async_subdev {
>   * @complete:	All subdevices have been probed successfully. The complete
>   *		callback is only executed for the root notifier.
>   * @unbind:	a subdevice is leaving
> + * @destroy:	the asd is about to be freed
>   */
>  struct v4l2_async_notifier_operations {
>  	int (*bound)(struct v4l2_async_notifier *notifier,
> @@ -90,6 +91,7 @@ struct v4l2_async_notifier_operations {
>  	void (*unbind)(struct v4l2_async_notifier *notifier,
>  		       struct v4l2_subdev *subdev,
>  		       struct v4l2_async_subdev *asd);
> +	void (*destroy)(struct v4l2_async_subdev *asd);
>  };
>  
>  /**

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances
@ 2022-06-15 22:36     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:36 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Sakari Ailus,
	Hans Verkuil

+ Sakari and Hans

This patch is needed by this series, but I think it could also be
reviewed and merged standalone already.

On Wed, Jun 15, 2022 at 04:10:48AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> Drivers typically extend the v4l2_async_subdev structure by embedding it
> in a driver-specific structure, to store per-subdev custom data. The
> v4l2_async_subdev instances are freed by the v4l2-async framework, which
> makes this mechanism cumbersome to use safely when custom data needs
> special treatment to be destroyed (such as freeing additional memory, or
> releasing references to kernel objects).
> 
> To ease this, add a .destroy() operation to the
> v4l2_async_notifier_operations structure. The operation is called right
> before the v4l2_async_subdev is freed, giving drivers a chance to
> destroy data if needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/v4l2-subdev.rst |  6 ++++++
>  drivers/media/v4l2-core/v4l2-async.c           | 10 ++++++++++
>  include/media/v4l2-async.h                     |  2 ++
>  3 files changed, 18 insertions(+)
> 
> diff --git a/Documentation/driver-api/media/v4l2-subdev.rst b/Documentation/driver-api/media/v4l2-subdev.rst
> index cf3b52bdbfb9..6f8d79926aa5 100644
> --- a/Documentation/driver-api/media/v4l2-subdev.rst
> +++ b/Documentation/driver-api/media/v4l2-subdev.rst
> @@ -243,6 +243,12 @@ notifier callback is called. After all subdevices have been located the
>  .complete() callback is called. When a subdevice is removed from the
>  system the .unbind() method is called. All three callbacks are optional.
>  
> +Drivers can store any type of custom data in their driver-specific
> +:c:type:`v4l2_async_subdev` wrapper. If any of that data requires special
> +handling when the structure is freed, drivers must implement the ``.destroy()``
> +notifier callback. The framework will call it right before freeing the
> +:c:type:`v4l2_async_subdev`.
> +
>  Calling subdev operations
>  ~~~~~~~~~~~~~~~~~~~~~~~~~
>  
> diff --git a/drivers/media/v4l2-core/v4l2-async.c b/drivers/media/v4l2-core/v4l2-async.c
> index c6995718237a..735dede624b8 100644
> --- a/drivers/media/v4l2-core/v4l2-async.c
> +++ b/drivers/media/v4l2-core/v4l2-async.c
> @@ -52,6 +52,15 @@ static int v4l2_async_nf_call_complete(struct v4l2_async_notifier *n)
>  	return n->ops->complete(n);
>  }
>  
> +static void v4l2_async_nf_call_destroy(struct v4l2_async_notifier *n,
> +				       struct v4l2_async_subdev *asd)
> +{
> +	if (!n->ops || !n->ops->destroy)
> +		return;
> +
> +	n->ops->destroy(asd);
> +}
> +
>  static bool match_i2c(struct v4l2_async_notifier *notifier,
>  		      struct v4l2_subdev *sd, struct v4l2_async_subdev *asd)
>  {
> @@ -626,6 +635,7 @@ static void __v4l2_async_nf_cleanup(struct v4l2_async_notifier *notifier)
>  		}
>  
>  		list_del(&asd->asd_list);
> +		v4l2_async_nf_call_destroy(notifier, asd);
>  		kfree(asd);
>  	}
>  }
> diff --git a/include/media/v4l2-async.h b/include/media/v4l2-async.h
> index 13ff3ad948f4..25eb1d138c06 100644
> --- a/include/media/v4l2-async.h
> +++ b/include/media/v4l2-async.h
> @@ -81,6 +81,7 @@ struct v4l2_async_subdev {
>   * @complete:	All subdevices have been probed successfully. The complete
>   *		callback is only executed for the root notifier.
>   * @unbind:	a subdevice is leaving
> + * @destroy:	the asd is about to be freed
>   */
>  struct v4l2_async_notifier_operations {
>  	int (*bound)(struct v4l2_async_notifier *notifier,
> @@ -90,6 +91,7 @@ struct v4l2_async_notifier_operations {
>  	void (*unbind)(struct v4l2_async_notifier *notifier,
>  		       struct v4l2_subdev *subdev,
>  		       struct v4l2_async_subdev *asd);
> +	void (*destroy)(struct v4l2_async_subdev *asd);
>  };
>  
>  /**

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-15 22:38     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:38 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Sakari Ailus,
	Hans Verkuil

+ Sakari and Hans

On Wed, Jun 15, 2022 at 04:11:09AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named
> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.
> 
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity
> -- 
> 2.30.2
> 

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-15 22:38     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:38 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Sakari Ailus,
	Hans Verkuil

+ Sakari and Hans

On Wed, Jun 15, 2022 at 04:11:09AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named
> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.
> 
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity
> -- 
> 2.30.2
> 

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-15 22:38     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:38 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Sakari Ailus,
	Hans Verkuil

+ Sakari and Hans

On Wed, Jun 15, 2022 at 04:11:10AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The newly added media_entity_remote_source_pad() helper function handles
> use cases where the entity has a link enabled uniqueness constraint
> covering all pads. There are use cases where the constraint covers a
> specific pad only. Add a new media_pad_remote_pad() function to handle
> this. It operates as media_entity_remote_source_pad(), but on a given
> pad instead of on the entity.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +--
>  drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
>  include/media/media-entity.h               | 18 +++++++++++++
>  3 files changed, 51 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index a2d1e32e3abb..83c3bdbf67be 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> -:c:func:`media_entity_remote_source_pad()`).
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
> +:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 1febf5a86be6..6429b0510bfb 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>  
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
> +{
> +	struct media_pad *found_pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &pad->entity->links, list) {
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (link->sink == pad)
> +			remote_pad = link->source;
> +		else if (link->source == pad)
> +			remote_pad = link->sink;
> +		else
> +			continue;
> +
> +		if (found_pad)
> +			return ERR_PTR(-ENOTUNIQ);
> +
> +		found_pad = remote_pad;
> +	}
> +
> +	if (!found_pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return found_pad;
> +}
> +EXPORT_SYMBOL_GPL(media_pad_remote_pad);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index 33d5f52719a0..bfe6a7b10a68 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
>  	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>  }
>  
> +/**
> + * media_pad_remote_pad - Find a remote pad connected to a pad
> + * @pad: The pad
> + *
> + * Search for and return a remote pad connected to @pad through an enabled
> + * link. If multiple (or no) remote pads are found, an error is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time on a given pad.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity
> -- 
> 2.30.2
> 

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
@ 2022-06-15 22:38     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:38 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip, Sakari Ailus,
	Hans Verkuil

+ Sakari and Hans

On Wed, Jun 15, 2022 at 04:11:10AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The newly added media_entity_remote_source_pad() helper function handles
> use cases where the entity has a link enabled uniqueness constraint
> covering all pads. There are use cases where the constraint covers a
> specific pad only. Add a new media_pad_remote_pad() function to handle
> this. It operates as media_entity_remote_source_pad(), but on a given
> pad instead of on the entity.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +--
>  drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
>  include/media/media-entity.h               | 18 +++++++++++++
>  3 files changed, 51 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index a2d1e32e3abb..83c3bdbf67be 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> -:c:func:`media_entity_remote_source_pad()`).
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
> +:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 1febf5a86be6..6429b0510bfb 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>  
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
> +{
> +	struct media_pad *found_pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &pad->entity->links, list) {
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (link->sink == pad)
> +			remote_pad = link->source;
> +		else if (link->source == pad)
> +			remote_pad = link->sink;
> +		else
> +			continue;
> +
> +		if (found_pad)
> +			return ERR_PTR(-ENOTUNIQ);
> +
> +		found_pad = remote_pad;
> +	}
> +
> +	if (!found_pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return found_pad;
> +}
> +EXPORT_SYMBOL_GPL(media_pad_remote_pad);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index 33d5f52719a0..bfe6a7b10a68 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
>  	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>  }
>  
> +/**
> + * media_pad_remote_pad - Find a remote pad connected to a pad
> + * @pad: The pad
> + *
> + * Search for and return a remote pad connected to @pad through an enabled
> + * link. If multiple (or no) remote pads are found, an error is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time on a given pad.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity
> -- 
> 2.30.2
> 

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-15 22:41     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:41 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:10:33AM +0900, Paul Elder wrote:
> Add a register dump file in debugfs for some of the buffer-related
> registers in MI, for the base address, the size, and the offset. Also
> dump the appropriate shadow registers.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
>  1 file changed, 21 insertions(+)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> index e76dc2b164b6..1a59c00fabdd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> @@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
>  }
>  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
>  
> +static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
> +{
> +	static const struct rkisp1_debug_register registers[] = {
> +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
> +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
> +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
> +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
> +		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
> +		{ /* Sentinel */ },
> +	};
> +	struct rkisp1_device *rkisp1 = m->private;
> +
> +	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
> +}
> +DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
> +
>  #define RKISP1_DEBUG_DATA_COUNT_BINS	32
>  #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
>  
> @@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
>  	debugfs_create_file("srsz", 0444, regs_dir,
>  			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
>  			    &rkisp1_debug_dump_rsz_regs_fops);
> +
> +	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
> +			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);

That's a very specialized file. I wonder if we should call it just
"mi_mp" if it needs to be extended later with other memory interface
registers for the main path. Or maybe even just "mi", to cover the self
path too ? The latter may be a tad too generic. What do you think ?

>  }
>  
>  void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
@ 2022-06-15 22:41     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 22:41 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:10:33AM +0900, Paul Elder wrote:
> Add a register dump file in debugfs for some of the buffer-related
> registers in MI, for the base address, the size, and the offset. Also
> dump the appropriate shadow registers.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
>  1 file changed, 21 insertions(+)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> index e76dc2b164b6..1a59c00fabdd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> @@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
>  }
>  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
>  
> +static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
> +{
> +	static const struct rkisp1_debug_register registers[] = {
> +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
> +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
> +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
> +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
> +		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
> +		{ /* Sentinel */ },
> +	};
> +	struct rkisp1_device *rkisp1 = m->private;
> +
> +	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
> +}
> +DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
> +
>  #define RKISP1_DEBUG_DATA_COUNT_BINS	32
>  #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
>  
> @@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
>  	debugfs_create_file("srsz", 0444, regs_dir,
>  			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
>  			    &rkisp1_debug_dump_rsz_regs_fops);
> +
> +	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
> +			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);

That's a very specialized file. I wonder if we should call it just
"mi_mp" if it needs to be extended later with other memory interface
registers for the main path. Or maybe even just "mi", to cover the self
path too ? The latter may be a tad too generic. What do you think ?

>  }
>  
>  void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-15 23:10     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 23:10 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:13AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> Connect the CSI receiver subdevice into the rest of the driver. This
> includes:
> - calling the subdevice via the v4l2 subdev API
> - moving the async notifier for the sensor from the ISP to the CSI
>   receiver
> - in the ISP, create a media link to the CSI receiver, and remove the
>   media link creation to the sensor
> - in the CSI receiver, create a media link to the sensor
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
>  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
>  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
>  4 files changed, 53 insertions(+), 44 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> index 8182694a6fe0..96712b467dde 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> @@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
>  		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
>  }
>  
> +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> +			   struct rkisp1_sensor_async *s_asd,
> +			   unsigned int source_pad)
> +{
> +	struct rkisp1_csi *csi = &rkisp1->csi;
> +	int ret;		

There's trailing whitespace here.

> +
> +	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> +						V4L2_CID_PIXEL_RATE);
> +	if (!s_asd->pixel_rate_ctrl) {
> +		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> +			sd->name);
> +		return -EINVAL;
> +	}
> +
> +	/* Create the link from the sensor to the CSI receiver. */
> +	ret = media_create_pad_link(&sd->entity, source_pad,
> +				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
> +				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> +	if (ret) {
> +		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
> +			sd->name);
> +		return ret;
> +	}
> +
> +	return 0;
> +}
> +
>  static int rkisp1_csi_config(struct rkisp1_csi *csi,
>  			     const struct rkisp1_sensor_async *sensor)
>  {
> @@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
>  		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>  }
>  
> -int rkisp1_csi_start(struct rkisp1_csi *csi,
> -		     const struct rkisp1_sensor_async *sensor)
> +static int rkisp1_csi_start(struct rkisp1_csi *csi,
> +			    const struct rkisp1_sensor_async *sensor)
>  {
>  	struct rkisp1_device *rkisp1 = csi->rkisp1;
>  	union phy_configure_opts opts;
> @@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
>  	return 0;
>  }
>  
> -void rkisp1_csi_stop(struct rkisp1_csi *csi)
> +static void rkisp1_csi_stop(struct rkisp1_csi *csi)
>  {
>  	rkisp1_csi_disable(csi);
>  
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> index ddf8e5e08f55..eadcd24f65fb 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> @@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>  int rkisp1_csi_register(struct rkisp1_device *rkisp1);
>  void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>  
> -int rkisp1_csi_start(struct rkisp1_csi *csi,
> -		     const struct rkisp1_sensor_async *sensor);
> -void rkisp1_csi_stop(struct rkisp1_csi *csi);
> +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> +			   struct rkisp1_sensor_async *s_asd,
> +			   unsigned int source_pad);
>  
>  #endif /* _RKISP1_CSI_H */
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index faf2cd4c8149..a3e182c86bdd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -17,6 +17,7 @@
>  #include <linux/pinctrl/consumer.h>
>  #include <linux/pm_runtime.h>
>  #include <media/v4l2-fwnode.h>
> +#include <media/v4l2-mc.h>
>  
>  #include "rkisp1-common.h"
>  #include "rkisp1-csi.h"
> @@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>  		container_of(asd, struct rkisp1_sensor_async, asd);
>  	int source_pad;
>  
> -	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> -						V4L2_CID_PIXEL_RATE);
> -	if (!s_asd->pixel_rate_ctrl) {
> -		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> -			sd->name);
> -		return -EINVAL;
> -	}
> -
>  	s_asd->sd = sd;
>  
> -	/* Create the link to the sensor. */
>  	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
>  						 MEDIA_PAD_FL_SOURCE);
>  	if (source_pad < 0) {
> @@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>  		return source_pad;
>  	}
>  
> -	return media_create_pad_link(&sd->entity, source_pad,
> -				     &rkisp1->isp.sd.entity,
> -				     RKISP1_ISP_PAD_SINK_VIDEO,
> -				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> +	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
>  }
>  
>  static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> @@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>  	unsigned int i;
>  	int ret;
>  
> +	/* Link the CSI receiver to the ISP. */
> +	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
> +				    &rkisp1->isp.sd.entity,
> +				    RKISP1_ISP_PAD_SINK_VIDEO,
> +				    MEDIA_LNK_FL_ENABLED);
> +	if (ret)
> +		return ret;
> +
>  	/* create ISP->RSZ->CAP links */
>  	for (i = 0; i < 2; i++) {
>  		struct media_entity *resizer =
> @@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
>  	if (ret)
>  		goto error;
>  
> -	ret = rkisp1_subdev_notifier_register(rkisp1);
> -	if (ret) {
> -		dev_err(rkisp1->dev,
> -			"Failed to register subdev notifier(%d)\n", ret);
> -		goto error;
> -	}
> -
>  	return 0;
>  
>  error:
> @@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
>  	if (ret)
>  		goto err_cleanup_csi;
>  
> +	ret = rkisp1_subdev_notifier_register(rkisp1);
> +	if (ret)
> +		goto err_unreg_entities;
> +
>  	rkisp1_debug_init(rkisp1);
>  
>  	return 0;
>  
> +err_unreg_entities:
> +	rkisp1_entities_unregister(rkisp1);
>  err_cleanup_csi:
>  	rkisp1_csi_cleanup(rkisp1);
>  err_unreg_media_dev:
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> index 5afb8be311c7..260c9ce0dca4 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> @@ -16,7 +16,6 @@
>  #include <media/v4l2-event.h>
>  
>  #include "rkisp1-common.h"
> -#include "rkisp1-csi.h"
>  
>  #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
>  #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
> @@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>  {
>  	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>  	struct rkisp1_device *rkisp1 = isp->rkisp1;
> -	const struct rkisp1_sensor_async *asd;
>  	struct media_pad *source_pad;
>  	int ret;
>  
>  	if (!enable) {
>  		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
> -
> -		rkisp1_csi_stop(&rkisp1->csi);
>  		rkisp1_isp_stop(isp);
> -
>  		return 0;
>  	}
>  
> @@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>  		return -EPIPE;
>  	}
>  
> -	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
> -			   asd);
> -
> -	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> -		return -EINVAL;
> +	if (rkisp1->source != &rkisp1->csi.sd)
> +		return -EPIPE;
>  
>  	isp->frame_sequence = -1;
>  	mutex_lock(&isp->ops_lock);
> -	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
> +	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
>  	if (ret)
>  		goto mutex_unlock;
>  
>  	rkisp1_isp_start(isp);
>  
> -	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> -	if (ret) {
> -		rkisp1_isp_stop(isp);
> -		goto mutex_unlock;
> -	}
> -
>  	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
>  	if (ret) {
>  		rkisp1_isp_stop(isp);
> -		rkisp1_csi_stop(&rkisp1->csi);
>  		goto mutex_unlock;
>  	}
>  
> -- 
> 2.30.2
> 

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
@ 2022-06-15 23:10     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-15 23:10 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:13AM +0900, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> Connect the CSI receiver subdevice into the rest of the driver. This
> includes:
> - calling the subdevice via the v4l2 subdev API
> - moving the async notifier for the sensor from the ISP to the CSI
>   receiver
> - in the ISP, create a media link to the CSI receiver, and remove the
>   media link creation to the sensor
> - in the CSI receiver, create a media link to the sensor
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
>  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
>  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
>  4 files changed, 53 insertions(+), 44 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> index 8182694a6fe0..96712b467dde 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> @@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
>  		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
>  }
>  
> +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> +			   struct rkisp1_sensor_async *s_asd,
> +			   unsigned int source_pad)
> +{
> +	struct rkisp1_csi *csi = &rkisp1->csi;
> +	int ret;		

There's trailing whitespace here.

> +
> +	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> +						V4L2_CID_PIXEL_RATE);
> +	if (!s_asd->pixel_rate_ctrl) {
> +		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> +			sd->name);
> +		return -EINVAL;
> +	}
> +
> +	/* Create the link from the sensor to the CSI receiver. */
> +	ret = media_create_pad_link(&sd->entity, source_pad,
> +				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
> +				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> +	if (ret) {
> +		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
> +			sd->name);
> +		return ret;
> +	}
> +
> +	return 0;
> +}
> +
>  static int rkisp1_csi_config(struct rkisp1_csi *csi,
>  			     const struct rkisp1_sensor_async *sensor)
>  {
> @@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
>  		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>  }
>  
> -int rkisp1_csi_start(struct rkisp1_csi *csi,
> -		     const struct rkisp1_sensor_async *sensor)
> +static int rkisp1_csi_start(struct rkisp1_csi *csi,
> +			    const struct rkisp1_sensor_async *sensor)
>  {
>  	struct rkisp1_device *rkisp1 = csi->rkisp1;
>  	union phy_configure_opts opts;
> @@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
>  	return 0;
>  }
>  
> -void rkisp1_csi_stop(struct rkisp1_csi *csi)
> +static void rkisp1_csi_stop(struct rkisp1_csi *csi)
>  {
>  	rkisp1_csi_disable(csi);
>  
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> index ddf8e5e08f55..eadcd24f65fb 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> @@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>  int rkisp1_csi_register(struct rkisp1_device *rkisp1);
>  void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>  
> -int rkisp1_csi_start(struct rkisp1_csi *csi,
> -		     const struct rkisp1_sensor_async *sensor);
> -void rkisp1_csi_stop(struct rkisp1_csi *csi);
> +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> +			   struct rkisp1_sensor_async *s_asd,
> +			   unsigned int source_pad);
>  
>  #endif /* _RKISP1_CSI_H */
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index faf2cd4c8149..a3e182c86bdd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -17,6 +17,7 @@
>  #include <linux/pinctrl/consumer.h>
>  #include <linux/pm_runtime.h>
>  #include <media/v4l2-fwnode.h>
> +#include <media/v4l2-mc.h>
>  
>  #include "rkisp1-common.h"
>  #include "rkisp1-csi.h"
> @@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>  		container_of(asd, struct rkisp1_sensor_async, asd);
>  	int source_pad;
>  
> -	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> -						V4L2_CID_PIXEL_RATE);
> -	if (!s_asd->pixel_rate_ctrl) {
> -		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> -			sd->name);
> -		return -EINVAL;
> -	}
> -
>  	s_asd->sd = sd;
>  
> -	/* Create the link to the sensor. */
>  	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
>  						 MEDIA_PAD_FL_SOURCE);
>  	if (source_pad < 0) {
> @@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>  		return source_pad;
>  	}
>  
> -	return media_create_pad_link(&sd->entity, source_pad,
> -				     &rkisp1->isp.sd.entity,
> -				     RKISP1_ISP_PAD_SINK_VIDEO,
> -				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> +	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
>  }
>  
>  static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> @@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>  	unsigned int i;
>  	int ret;
>  
> +	/* Link the CSI receiver to the ISP. */
> +	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
> +				    &rkisp1->isp.sd.entity,
> +				    RKISP1_ISP_PAD_SINK_VIDEO,
> +				    MEDIA_LNK_FL_ENABLED);
> +	if (ret)
> +		return ret;
> +
>  	/* create ISP->RSZ->CAP links */
>  	for (i = 0; i < 2; i++) {
>  		struct media_entity *resizer =
> @@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
>  	if (ret)
>  		goto error;
>  
> -	ret = rkisp1_subdev_notifier_register(rkisp1);
> -	if (ret) {
> -		dev_err(rkisp1->dev,
> -			"Failed to register subdev notifier(%d)\n", ret);
> -		goto error;
> -	}
> -
>  	return 0;
>  
>  error:
> @@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
>  	if (ret)
>  		goto err_cleanup_csi;
>  
> +	ret = rkisp1_subdev_notifier_register(rkisp1);
> +	if (ret)
> +		goto err_unreg_entities;
> +
>  	rkisp1_debug_init(rkisp1);
>  
>  	return 0;
>  
> +err_unreg_entities:
> +	rkisp1_entities_unregister(rkisp1);
>  err_cleanup_csi:
>  	rkisp1_csi_cleanup(rkisp1);
>  err_unreg_media_dev:
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> index 5afb8be311c7..260c9ce0dca4 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> @@ -16,7 +16,6 @@
>  #include <media/v4l2-event.h>
>  
>  #include "rkisp1-common.h"
> -#include "rkisp1-csi.h"
>  
>  #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
>  #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
> @@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>  {
>  	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>  	struct rkisp1_device *rkisp1 = isp->rkisp1;
> -	const struct rkisp1_sensor_async *asd;
>  	struct media_pad *source_pad;
>  	int ret;
>  
>  	if (!enable) {
>  		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
> -
> -		rkisp1_csi_stop(&rkisp1->csi);
>  		rkisp1_isp_stop(isp);
> -
>  		return 0;
>  	}
>  
> @@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>  		return -EPIPE;
>  	}
>  
> -	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
> -			   asd);
> -
> -	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> -		return -EINVAL;
> +	if (rkisp1->source != &rkisp1->csi.sd)
> +		return -EPIPE;
>  
>  	isp->frame_sequence = -1;
>  	mutex_lock(&isp->ops_lock);
> -	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
> +	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
>  	if (ret)
>  		goto mutex_unlock;
>  
>  	rkisp1_isp_start(isp);
>  
> -	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> -	if (ret) {
> -		rkisp1_isp_stop(isp);
> -		goto mutex_unlock;
> -	}
> -
>  	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
>  	if (ret) {
>  		rkisp1_isp_stop(isp);
> -		rkisp1_csi_stop(&rkisp1->csi);
>  		goto mutex_unlock;
>  	}
>  
> -- 
> 2.30.2
> 

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 00/55] media: rkisp1: Cleanups and add support for i.MX8MP
  2022-06-14 19:10 ` Paul Elder
@ 2022-06-16  0:19   ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  0:19 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patches.

On Wed, Jun 15, 2022 at 04:10:32AM +0900, Paul Elder wrote:
> Hello,
> 
> This series depends on v4 of "media: rkisp1: Misc bug fixes and cleanups" [1].
> 
> The ISP integrated in the i.MX8MP is nearly the same as the rkisp1, and
> so we can reuse the rkisp1 driver for it.
> 
> This series does some cleanup and refactoring of the rkisp1 driver,
> (patches 1/55 to 46/55), and then adds support for the i.MX8MP (patches
> 47/55 to 55/55).

I have a few questions about the i.MX8MP support (the main one being
about the version numbering scheme), which I'll ask in replies to the
corresponding patches. Patches 01/55 to 46/55 could be merged already,
once reviewed of course. As the series is large, let's see if we can
motivate any reviewer :-)

> [1] https://lore.kernel.org/linux-media/Ymbxs2p9Tuf331qM@pendragon.ideasonboard.com/T/
> 
> Laurent Pinchart (38):
>   media: rkisp1: Enable compilation on ARCH_MXC
>   media: rkisp1: Disable runtime PM in probe error path
>   media: rkisp1: Read the ID register at probe time instead of streamon
>   media: rkisp1: Rename rkisp1_match_data to rkisp1_info
>   media: rkisp1: Access ISP version from info pointer
>   media: rkisp1: cap: Print debug message on failed link validation
>   media: rkisp1: Move sensor .s_stream() call to ISP
>   media: rkisp1: Reject sensors without pixel rate control at bound time
>   media: rkisp1: Create link from sensor to ISP at notifier bound time
>   media: rkisp1: Create internal links at probe time
>   media: rkisp1: Rename rkisp1_subdev_notifier() to
>     rkisp1_subdev_notifier_register()
>   media: v4l2-async: Add notifier operation to destroy asd instances
>   media: rkisp1: Fix sensor source pad retrieval at bound time
>   media: rkisp1: isp: Start CSI-2 receiver before ISP
>   media: rkisp1: csi: Handle CSI-2 RX configuration fully in
>     rkisp1-csi.c
>   media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi
>     prefix
>   media: rkisp1: csi: Move start delay to rkisp1_csi_start()
>   media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
>   media: rkisp1: csi: Constify argument to rkisp1_csi_start()
>   media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
>   media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
>   media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
>   media: rkisp1: isp: Add container_of wrapper to cast subdev to
>     rkisp1_isp
>   media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
>   media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
>   media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
>   media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single
>     variable
>   media: rkisp1: isp: Initialize some variables at declaration time
>   media: rkisp1: isp: Fix whitespace issues
>   media: rkisp1: isp: Constify various local variables
>   media: rkisp1: isp: Rename rkisp1_get_remote_source()
>   media: mc-entity: Add a new helper function to get a remote pad
>   media: mc-entity: Add a new helper function to get a remote pad for a
>     pad
>   media: rkisp1: isp: Disallow multiple active sources
>   media: rkisp1: csi: Plumb the CSI RX subdev
>   media: rkisp1: Add infrastructure to support ISP features
>   media: rkisp1: Make the internal CSI-2 receiver optional
>   media: rkisp1: Configure gasket on i.MX8MP
> 
> Paul Elder (17):
>   media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
>   media: rkisp1: debug: Add debugfs files to monitor MI and ISP
>     interrupts
>   media: rkisp1: Save info pointer in rkisp1_device
>   media: rkisp1: Make rkisp1_isp_mbus_info common
>   media: rkisp1: Split CSI handling to separate file
>   media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
>   media: rkisp1: Use fwnode_graph_for_each_endpoint
>   dt-bindings: media: rkisp1: Add port for parallel interface
>   media: rkisp1: Support the ISP parallel input
>   dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
>   media: rkisp1: Add match data for i.MX8MP ISP
>   media: rkisp1: Add and set registers for crop for i.MX8MP
>   media: rkisp1: Add and set registers for output size config on i.MX8MP
>   media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
>   media: rkisp1: Shift DMA buffer addresses on i.MX8MP
>   media: rkisp1: Add register definitions for the test pattern generator
>   media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
> 
>  .../bindings/media/rockchip-isp1.yaml         |  30 +-
>  Documentation/driver-api/media/mc-core.rst    |   4 +-
>  .../driver-api/media/v4l2-subdev.rst          |   6 +
>  drivers/media/mc/mc-entity.c                  |  69 ++
>  .../media/platform/rockchip/rkisp1/Kconfig    |   2 +-
>  .../media/platform/rockchip/rkisp1/Makefile   |   1 +
>  .../platform/rockchip/rkisp1/rkisp1-capture.c |  49 +-
>  .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 ++++
>  .../platform/rockchip/rkisp1/rkisp1-common.h  | 130 +++-
>  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 525 ++++++++++++++
>  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   |  55 +-
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 440 +++++++-----
>  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 679 +++++++-----------
>  .../platform/rockchip/rkisp1/rkisp1-params.c  |   2 +-
>  .../platform/rockchip/rkisp1/rkisp1-regs.h    |  87 +++
>  .../platform/rockchip/rkisp1/rkisp1-resizer.c |  43 +-
>  .../platform/rockchip/rkisp1/rkisp1-stats.c   |   4 +-
>  drivers/media/v4l2-core/v4l2-async.c          |  10 +
>  include/media/media-entity.h                  |  63 ++
>  include/media/v4l2-async.h                    |   2 +
>  include/uapi/linux/rkisp1-config.h            |   3 +
>  22 files changed, 1735 insertions(+), 645 deletions(-)
>  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 00/55] media: rkisp1: Cleanups and add support for i.MX8MP
@ 2022-06-16  0:19   ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  0:19 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patches.

On Wed, Jun 15, 2022 at 04:10:32AM +0900, Paul Elder wrote:
> Hello,
> 
> This series depends on v4 of "media: rkisp1: Misc bug fixes and cleanups" [1].
> 
> The ISP integrated in the i.MX8MP is nearly the same as the rkisp1, and
> so we can reuse the rkisp1 driver for it.
> 
> This series does some cleanup and refactoring of the rkisp1 driver,
> (patches 1/55 to 46/55), and then adds support for the i.MX8MP (patches
> 47/55 to 55/55).

I have a few questions about the i.MX8MP support (the main one being
about the version numbering scheme), which I'll ask in replies to the
corresponding patches. Patches 01/55 to 46/55 could be merged already,
once reviewed of course. As the series is large, let's see if we can
motivate any reviewer :-)

> [1] https://lore.kernel.org/linux-media/Ymbxs2p9Tuf331qM@pendragon.ideasonboard.com/T/
> 
> Laurent Pinchart (38):
>   media: rkisp1: Enable compilation on ARCH_MXC
>   media: rkisp1: Disable runtime PM in probe error path
>   media: rkisp1: Read the ID register at probe time instead of streamon
>   media: rkisp1: Rename rkisp1_match_data to rkisp1_info
>   media: rkisp1: Access ISP version from info pointer
>   media: rkisp1: cap: Print debug message on failed link validation
>   media: rkisp1: Move sensor .s_stream() call to ISP
>   media: rkisp1: Reject sensors without pixel rate control at bound time
>   media: rkisp1: Create link from sensor to ISP at notifier bound time
>   media: rkisp1: Create internal links at probe time
>   media: rkisp1: Rename rkisp1_subdev_notifier() to
>     rkisp1_subdev_notifier_register()
>   media: v4l2-async: Add notifier operation to destroy asd instances
>   media: rkisp1: Fix sensor source pad retrieval at bound time
>   media: rkisp1: isp: Start CSI-2 receiver before ISP
>   media: rkisp1: csi: Handle CSI-2 RX configuration fully in
>     rkisp1-csi.c
>   media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi
>     prefix
>   media: rkisp1: csi: Move start delay to rkisp1_csi_start()
>   media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
>   media: rkisp1: csi: Constify argument to rkisp1_csi_start()
>   media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
>   media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
>   media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
>   media: rkisp1: isp: Add container_of wrapper to cast subdev to
>     rkisp1_isp
>   media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
>   media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
>   media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
>   media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single
>     variable
>   media: rkisp1: isp: Initialize some variables at declaration time
>   media: rkisp1: isp: Fix whitespace issues
>   media: rkisp1: isp: Constify various local variables
>   media: rkisp1: isp: Rename rkisp1_get_remote_source()
>   media: mc-entity: Add a new helper function to get a remote pad
>   media: mc-entity: Add a new helper function to get a remote pad for a
>     pad
>   media: rkisp1: isp: Disallow multiple active sources
>   media: rkisp1: csi: Plumb the CSI RX subdev
>   media: rkisp1: Add infrastructure to support ISP features
>   media: rkisp1: Make the internal CSI-2 receiver optional
>   media: rkisp1: Configure gasket on i.MX8MP
> 
> Paul Elder (17):
>   media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
>   media: rkisp1: debug: Add debugfs files to monitor MI and ISP
>     interrupts
>   media: rkisp1: Save info pointer in rkisp1_device
>   media: rkisp1: Make rkisp1_isp_mbus_info common
>   media: rkisp1: Split CSI handling to separate file
>   media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
>   media: rkisp1: Use fwnode_graph_for_each_endpoint
>   dt-bindings: media: rkisp1: Add port for parallel interface
>   media: rkisp1: Support the ISP parallel input
>   dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
>   media: rkisp1: Add match data for i.MX8MP ISP
>   media: rkisp1: Add and set registers for crop for i.MX8MP
>   media: rkisp1: Add and set registers for output size config on i.MX8MP
>   media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
>   media: rkisp1: Shift DMA buffer addresses on i.MX8MP
>   media: rkisp1: Add register definitions for the test pattern generator
>   media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
> 
>  .../bindings/media/rockchip-isp1.yaml         |  30 +-
>  Documentation/driver-api/media/mc-core.rst    |   4 +-
>  .../driver-api/media/v4l2-subdev.rst          |   6 +
>  drivers/media/mc/mc-entity.c                  |  69 ++
>  .../media/platform/rockchip/rkisp1/Kconfig    |   2 +-
>  .../media/platform/rockchip/rkisp1/Makefile   |   1 +
>  .../platform/rockchip/rkisp1/rkisp1-capture.c |  49 +-
>  .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 ++++
>  .../platform/rockchip/rkisp1/rkisp1-common.h  | 130 +++-
>  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 525 ++++++++++++++
>  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   |  55 +-
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 440 +++++++-----
>  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 679 +++++++-----------
>  .../platform/rockchip/rkisp1/rkisp1-params.c  |   2 +-
>  .../platform/rockchip/rkisp1/rkisp1-regs.h    |  87 +++
>  .../platform/rockchip/rkisp1/rkisp1-resizer.c |  43 +-
>  .../platform/rockchip/rkisp1/rkisp1-stats.c   |   4 +-
>  drivers/media/v4l2-core/v4l2-async.c          |  10 +
>  include/media/media-entity.h                  |  63 ++
>  include/media/v4l2-async.h                    |   2 +
>  include/uapi/linux/rkisp1-config.h            |   3 +
>  22 files changed, 1735 insertions(+), 645 deletions(-)
>  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-16  0:44     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  0:44 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:10:35AM +0900, Paul Elder wrote:
> Add files in debugfs to monitor some of the interrupts of the MI and
> ISP. Add the appropriate holder variables in the rkisp1_debug struct as
> well.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  9 +++++++++
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 20 +++++++++++++++++++
>  2 files changed, 29 insertions(+)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 4243ff5e2197..a67fe7b1dfa1 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -364,6 +364,15 @@ struct rkisp1_debug {
>  	unsigned long stats_error;
>  	unsigned long stop_timeout[2];
>  	unsigned long frame_drop[2];
> +	unsigned long mi_irq_mblk_line_count;
> +	unsigned long mi_irq_fill_mp_y_count;
> +	unsigned long mi_irq_frame_count;
> +	unsigned long mi_irq_wrap_mp_y_count;
> +	unsigned long mi_irq_wrap_mp_cb_count;
> +	unsigned long mi_irq_wrap_mp_cr_count;
> +	unsigned long isp_irq_v_start_count;
> +	unsigned long isp_irq_frame_count;
> +	unsigned long isp_irq_frame_in_count;
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> index 1a59c00fabdd..02854e8ea1a4 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> @@ -220,6 +220,26 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
>  	debugfs_create_file("input_status", 0444, debug->debugfs_dir, rkisp1,
>  			    &rkisp1_debug_input_status_fops);
>  
> +	debugfs_create_ulong("mi_irq_mblk_line_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_mblk_line_count);
> +	debugfs_create_ulong("mi_irq_fill_mp_y_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_fill_mp_y_count);
> +	debugfs_create_ulong("mi_irq_frame_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_frame_count);
> +	debugfs_create_ulong("mi_irq_wrap_mp_y_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_wrap_mp_y_count);
> +	debugfs_create_ulong("mi_irq_wrap_mp_cb_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_wrap_mp_cb_count);
> +	debugfs_create_ulong("mi_irq_wrap_mp_cr_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_wrap_mp_cr_count);
> +
> +	debugfs_create_ulong("isp_irq_v_start_count", 0444, debug->debugfs_dir,
> +			     &debug->isp_irq_v_start_count);
> +	debugfs_create_ulong("isp_irq_frame_count", 0444, debug->debugfs_dir,
> +			     &debug->isp_irq_frame_count);
> +	debugfs_create_ulong("isp_irq_frame_in_count", 0444, debug->debugfs_dir,
> +			     &debug->isp_irq_frame_in_count);

It's nice to expose these through debugfs, but it looks like you never
actually set any of those fields :-) I think you could just drop this
patch.

> +
>  	regs_dir = debugfs_create_dir("regs", debug->debugfs_dir);
>  
>  	debugfs_create_file("core", 0444, regs_dir, rkisp1,

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts
@ 2022-06-16  0:44     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  0:44 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:10:35AM +0900, Paul Elder wrote:
> Add files in debugfs to monitor some of the interrupts of the MI and
> ISP. Add the appropriate holder variables in the rkisp1_debug struct as
> well.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  9 +++++++++
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 20 +++++++++++++++++++
>  2 files changed, 29 insertions(+)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 4243ff5e2197..a67fe7b1dfa1 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -364,6 +364,15 @@ struct rkisp1_debug {
>  	unsigned long stats_error;
>  	unsigned long stop_timeout[2];
>  	unsigned long frame_drop[2];
> +	unsigned long mi_irq_mblk_line_count;
> +	unsigned long mi_irq_fill_mp_y_count;
> +	unsigned long mi_irq_frame_count;
> +	unsigned long mi_irq_wrap_mp_y_count;
> +	unsigned long mi_irq_wrap_mp_cb_count;
> +	unsigned long mi_irq_wrap_mp_cr_count;
> +	unsigned long isp_irq_v_start_count;
> +	unsigned long isp_irq_frame_count;
> +	unsigned long isp_irq_frame_in_count;
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> index 1a59c00fabdd..02854e8ea1a4 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> @@ -220,6 +220,26 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
>  	debugfs_create_file("input_status", 0444, debug->debugfs_dir, rkisp1,
>  			    &rkisp1_debug_input_status_fops);
>  
> +	debugfs_create_ulong("mi_irq_mblk_line_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_mblk_line_count);
> +	debugfs_create_ulong("mi_irq_fill_mp_y_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_fill_mp_y_count);
> +	debugfs_create_ulong("mi_irq_frame_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_frame_count);
> +	debugfs_create_ulong("mi_irq_wrap_mp_y_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_wrap_mp_y_count);
> +	debugfs_create_ulong("mi_irq_wrap_mp_cb_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_wrap_mp_cb_count);
> +	debugfs_create_ulong("mi_irq_wrap_mp_cr_count", 0444, debug->debugfs_dir,
> +			     &debug->mi_irq_wrap_mp_cr_count);
> +
> +	debugfs_create_ulong("isp_irq_v_start_count", 0444, debug->debugfs_dir,
> +			     &debug->isp_irq_v_start_count);
> +	debugfs_create_ulong("isp_irq_frame_count", 0444, debug->debugfs_dir,
> +			     &debug->isp_irq_frame_count);
> +	debugfs_create_ulong("isp_irq_frame_in_count", 0444, debug->debugfs_dir,
> +			     &debug->isp_irq_frame_in_count);

It's nice to expose these through debugfs, but it looks like you never
actually set any of those fields :-) I think you could just drop this
patch.

> +
>  	regs_dir = debugfs_create_dir("regs", debug->debugfs_dir);
>  
>  	debugfs_create_file("core", 0444, regs_dir, rkisp1,

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-16  0:50     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  0:50 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:10:41AM +0900, Paul Elder wrote:
> The upcoming CSI receiver split from the ISP to a separate source file
> will need to be able to access the list of formats supported by the
> driver. Move it out of the ISP's header and into the common header, and
> add helper functions for accessing it so that the format list doesn't
> need to be stored in the header.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 +++++++++++++++
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  28 ++-
>  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 168 ++----------------
>  .../platform/rockchip/rkisp1/rkisp1-resizer.c |  14 +-
>  .../platform/rockchip/rkisp1/rkisp1-stats.c   |   2 +-
>  5 files changed, 193 insertions(+), 167 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
> index cf889666e166..bb0ea20118e1 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
> @@ -5,10 +5,158 @@
>   * Copyright (C) 2019 Collabora, Ltd.
>   */
>  
> +#include <media/mipi-csi2.h>
>  #include <media/v4l2-rect.h>
>  
>  #include "rkisp1-common.h"
>  
> +static const struct rkisp1_mbus_info rkisp1_formats[] = {
> +	{
> +		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.direction	= RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_RGGB,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_BGGR,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_GBRG,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_GRBG,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_RGGB,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_BGGR,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_GBRG,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_GRBG,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_RGGB,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_BGGR,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_GBRG,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_GRBG,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	},
> +};
> +
> +unsigned int rkisp1_mbus_info_length(void)
> +{
> +	return ARRAY_SIZE(rkisp1_formats);
> +}
> +
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index)
> +{
> +	if (index >= rkisp1_mbus_info_length())

	if (index >= ARRAY_SIZE(rkisp1_formats))

to match the code below (and see also my comment further down)

> +		return NULL;
> +
> +	return &rkisp1_formats[index];
> +}
> +
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code)
> +{
> +	unsigned int i;
> +
> +	for (i = 0; i < ARRAY_SIZE(rkisp1_formats); i++) {
> +		const struct rkisp1_mbus_info *fmt = &rkisp1_formats[i];
> +
> +		if (fmt->mbus_code == mbus_code)
> +			return fmt;
> +	}
> +
> +	return NULL;
> +}
> +
>  static const struct v4l2_rect rkisp1_sd_min_crop = {
>  	.width = RKISP1_ISP_MIN_WIDTH,
>  	.height = RKISP1_ISP_MIN_HEIGHT,
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 50d31a254b03..c7d5c57607bd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -26,7 +26,7 @@
>  struct dentry;
>  
>  /*
> - * flags on the 'direction' field in struct 'rkisp1_isp_mbus_info' that indicate
> + * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
>   * on which pad the media bus format is supported
>   */
>  #define RKISP1_ISP_SD_SRC			BIT(0)
> @@ -150,8 +150,8 @@ struct rkisp1_isp {
>  	struct v4l2_subdev sd;
>  	struct media_pad pads[RKISP1_ISP_PAD_MAX];
>  	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
> -	const struct rkisp1_isp_mbus_info *sink_fmt;
> -	const struct rkisp1_isp_mbus_info *src_fmt;
> +	const struct rkisp1_mbus_info *sink_fmt;
> +	const struct rkisp1_mbus_info *src_fmt;
>  	struct mutex ops_lock; /* serialize the subdevice ops */
>  	bool is_dphy_errctrl_disabled;
>  	__u32 frame_sequence;
> @@ -438,8 +438,8 @@ struct rkisp1_device {
>  };
>  
>  /*
> - * struct rkisp1_isp_mbus_info - ISP media bus info, Translates media bus code to hardware
> - *				 format values
> + * struct rkisp1_mbus_info - ISP media bus info, Translates media bus code to hardware
> + *			     format values
>   *
>   * @mbus_code: media bus code
>   * @pixel_enc: pixel encoding
> @@ -449,7 +449,7 @@ struct rkisp1_device {
>   * @bayer_pat: bayer pattern
>   * @direction: a bitmask of the flags indicating on which pad the format is supported on
>   */
> -struct rkisp1_isp_mbus_info {
> +struct rkisp1_mbus_info {
>  	u32 mbus_code;
>  	enum v4l2_pixel_encoding pixel_enc;
>  	u32 mipi_dt;
> @@ -481,6 +481,18 @@ static inline u32 rkisp1_read(struct rkisp1_device *rkisp1, unsigned int addr)
>  int rkisp1_cap_enum_mbus_codes(struct rkisp1_capture *cap,
>  			       struct v4l2_subdev_mbus_code_enum *code);
>  
> +/*
> + * rkisp1_mbus_info_length - Return the number of supported mbus codes
> + */
> +unsigned int rkisp1_mbus_info_length(void);
> +
> +/*
> + * rkisp1_mbus_info_get_by_index - Retrieve the ith supported mbus info
> + *
> + * @index: index of the mbus info to fetch
> + */
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index);
> +
>  /*
>   * rkisp1_sd_adjust_crop_rect - adjust a rectangle to fit into another rectangle.
>   *
> @@ -500,11 +512,11 @@ void rkisp1_sd_adjust_crop(struct v4l2_rect *crop,
>  			   const struct v4l2_mbus_framefmt *bounds);
>  
>  /*
> - * rkisp1_isp_mbus_info - get the isp info of the media bus code
> + * rkisp1_mbus_info_get_by_code - get the isp info of the media bus code
>   *
>   * @mbus_code: the media bus code
>   */
> -const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code);
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code);
>  
>  /* rkisp1_params_configure - configure the params when stream starts.
>   *			     This function is called by the isp entity upon stream starts.
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> index 328e8fec14e9..89577119b571 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> @@ -15,7 +15,6 @@
>  #include <linux/videodev2.h>
>  #include <linux/vmalloc.h>
>  
> -#include <media/mipi-csi2.h>
>  #include <media/v4l2-event.h>
>  
>  #include "rkisp1-common.h"
> @@ -56,144 +55,10 @@
>   * +---------------------------------------------------------+
>   */
>  
> -static const struct rkisp1_isp_mbus_info rkisp1_isp_formats[] = {
> -	{
> -		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.direction	= RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_RGGB,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_BGGR,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_GBRG,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_GRBG,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_RGGB,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_BGGR,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_GBRG,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_GRBG,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_RGGB,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_BGGR,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_GBRG,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_GRBG,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	},
> -};
> -
>  /* ----------------------------------------------------------------------------
>   * Helpers
>   */
>  
> -const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code)
> -{
> -	unsigned int i;
> -
> -	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
> -		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
> -
> -		if (fmt->mbus_code == mbus_code)
> -			return fmt;
> -	}
> -
> -	return NULL;
> -}
> -
>  static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
>  {
>  	struct media_pad *local, *remote;
> @@ -275,7 +140,7 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
>  static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>  {
>  	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
> -	const struct rkisp1_isp_mbus_info *src_fmt, *sink_fmt;
> +	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
>  	struct rkisp1_sensor_async *sensor;
>  	struct v4l2_mbus_framefmt *sink_frm;
>  	struct v4l2_rect *sink_crop;
> @@ -376,7 +241,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>  
>  static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>  {
> -	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> +	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>  	u32 val, input_sel;
>  
>  	switch (sink_fmt->bus_width) {
> @@ -402,7 +267,7 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>  
>  static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
>  {
> -	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> +	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>  	unsigned int lanes = rkisp1->active_sensor->lanes;
>  	u32 mipi_ctrl;
>  
> @@ -593,11 +458,12 @@ static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
>  		return 0;
>  	}
>  
> -	if (code->index >= ARRAY_SIZE(rkisp1_isp_formats))
> +	if (code->index >= rkisp1_mbus_info_length())
>  		return -EINVAL;
>  
> -	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
> -		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
> +	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
> +		const struct rkisp1_mbus_info *fmt =
> +			rkisp1_mbus_info_get_by_index(i);

You could write this as

	for (i = 0; ; i++) {
		const struct rkisp1_mbus_info *fmt =
			rkisp1_mbus_info_get_by_index(i);

		if (!fmt)
			return -EINVAL;

and drop the rkisp1_mbus_info_length() function. Up to you. Either way,

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

>  
>  		if (fmt->direction & dir)
>  			pos++;
> @@ -619,7 +485,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
>  				      struct v4l2_subdev_state *sd_state,
>  				      struct v4l2_subdev_frame_size_enum *fse)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  
>  	if (fse->pad == RKISP1_ISP_PAD_SINK_PARAMS ||
>  	    fse->pad == RKISP1_ISP_PAD_SOURCE_STATS)
> @@ -628,7 +494,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
>  	if (fse->index > 0)
>  		return -EINVAL;
>  
> -	mbus_info = rkisp1_isp_mbus_info_get(fse->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(fse->code);
>  	if (!mbus_info)
>  		return -EINVAL;
>  
> @@ -695,7 +561,7 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
>  				   struct v4l2_mbus_framefmt *format,
>  				   unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *src_fmt;
>  	const struct v4l2_rect *src_crop;
>  
> @@ -705,10 +571,10 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
>  					   RKISP1_ISP_PAD_SOURCE_VIDEO, which);
>  
>  	src_fmt->code = format->code;
> -	mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
>  	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
>  		src_fmt->code = RKISP1_DEF_SRC_PAD_FMT;
> -		mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
> +		mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
>  	}
>  	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
>  		isp->src_fmt = mbus_info;
> @@ -793,7 +659,7 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
>  				    struct v4l2_mbus_framefmt *format,
>  				    unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *sink_fmt;
>  	struct v4l2_rect *sink_crop;
>  
> @@ -801,10 +667,10 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
>  					  RKISP1_ISP_PAD_SINK_VIDEO,
>  					  which);
>  	sink_fmt->code = format->code;
> -	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
>  		sink_fmt->code = RKISP1_DEF_SINK_PAD_FMT;
> -		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	}
>  	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
>  		isp->sink_fmt = mbus_info;
> @@ -1080,8 +946,8 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
>  	pads[RKISP1_ISP_PAD_SOURCE_VIDEO].flags = MEDIA_PAD_FL_SOURCE;
>  	pads[RKISP1_ISP_PAD_SOURCE_STATS].flags = MEDIA_PAD_FL_SOURCE;
>  
> -	isp->sink_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SINK_PAD_FMT);
> -	isp->src_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SRC_PAD_FMT);
> +	isp->sink_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SINK_PAD_FMT);
> +	isp->src_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SRC_PAD_FMT);
>  
>  	mutex_init(&isp->ops_lock);
>  	ret = media_entity_pads_init(&sd->entity, RKISP1_ISP_PAD_MAX, pads);
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> index 1c07985c810d..f4caa8f684aa 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> @@ -433,14 +433,14 @@ static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
>  				   struct v4l2_mbus_framefmt *format,
>  				   unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *sink_mbus_info;
> +	const struct rkisp1_mbus_info *sink_mbus_info;
>  	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
>  
>  	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
>  					  which);
>  	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
>  					 which);
> -	sink_mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  
>  	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
>  	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
> @@ -462,7 +462,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
>  				     struct v4l2_rect *r,
>  				     unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *sink_fmt;
>  	struct v4l2_rect *sink_crop;
>  
> @@ -473,7 +473,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
>  					    which);
>  
>  	/* Not crop for MP bayer raw data */
> -	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  
>  	if (rsz->id == RKISP1_MAINPATH &&
>  	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
> @@ -500,7 +500,7 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
>  				    struct v4l2_mbus_framefmt *format,
>  				    unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>  	struct v4l2_rect *sink_crop;
>  
> @@ -516,10 +516,10 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
>  	else
>  		sink_fmt->code = format->code;
>  
> -	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
>  		sink_fmt->code = RKISP1_DEF_FMT;
> -		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	}
>  	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
>  		rsz->pixel_enc = mbus_info->pixel_enc;
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
> index 7d82356b5345..2795eef91bdd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
> @@ -305,7 +305,7 @@ static void rkisp1_stats_get_bls_meas(struct rkisp1_stats *stats,
>  				      struct rkisp1_stat_buffer *pbuf)
>  {
>  	struct rkisp1_device *rkisp1 = stats->rkisp1;
> -	const struct rkisp1_isp_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
> +	const struct rkisp1_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
>  	struct rkisp1_cif_isp_bls_meas_val *bls_val;
>  
>  	bls_val = &pbuf->params.ae.bls_val;

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common
@ 2022-06-16  0:50     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  0:50 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:10:41AM +0900, Paul Elder wrote:
> The upcoming CSI receiver split from the ISP to a separate source file
> will need to be able to access the list of formats supported by the
> driver. Move it out of the ISP's header and into the common header, and
> add helper functions for accessing it so that the format list doesn't
> need to be stored in the header.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 +++++++++++++++
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  28 ++-
>  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 168 ++----------------
>  .../platform/rockchip/rkisp1/rkisp1-resizer.c |  14 +-
>  .../platform/rockchip/rkisp1/rkisp1-stats.c   |   2 +-
>  5 files changed, 193 insertions(+), 167 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
> index cf889666e166..bb0ea20118e1 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
> @@ -5,10 +5,158 @@
>   * Copyright (C) 2019 Collabora, Ltd.
>   */
>  
> +#include <media/mipi-csi2.h>
>  #include <media/v4l2-rect.h>
>  
>  #include "rkisp1-common.h"
>  
> +static const struct rkisp1_mbus_info rkisp1_formats[] = {
> +	{
> +		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.direction	= RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_RGGB,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_BGGR,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_GBRG,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> +		.bayer_pat	= RKISP1_RAW_GRBG,
> +		.bus_width	= 10,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_RGGB,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_BGGR,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_GBRG,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> +		.bayer_pat	= RKISP1_RAW_GRBG,
> +		.bus_width	= 12,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_RGGB,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_BGGR,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_GBRG,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
> +		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> +		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> +		.bayer_pat	= RKISP1_RAW_GRBG,
> +		.bus_width	= 8,
> +		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	}, {
> +		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
> +		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> +		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> +		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
> +		.bus_width	= 16,
> +		.direction	= RKISP1_ISP_SD_SINK,
> +	},
> +};
> +
> +unsigned int rkisp1_mbus_info_length(void)
> +{
> +	return ARRAY_SIZE(rkisp1_formats);
> +}
> +
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index)
> +{
> +	if (index >= rkisp1_mbus_info_length())

	if (index >= ARRAY_SIZE(rkisp1_formats))

to match the code below (and see also my comment further down)

> +		return NULL;
> +
> +	return &rkisp1_formats[index];
> +}
> +
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code)
> +{
> +	unsigned int i;
> +
> +	for (i = 0; i < ARRAY_SIZE(rkisp1_formats); i++) {
> +		const struct rkisp1_mbus_info *fmt = &rkisp1_formats[i];
> +
> +		if (fmt->mbus_code == mbus_code)
> +			return fmt;
> +	}
> +
> +	return NULL;
> +}
> +
>  static const struct v4l2_rect rkisp1_sd_min_crop = {
>  	.width = RKISP1_ISP_MIN_WIDTH,
>  	.height = RKISP1_ISP_MIN_HEIGHT,
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 50d31a254b03..c7d5c57607bd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -26,7 +26,7 @@
>  struct dentry;
>  
>  /*
> - * flags on the 'direction' field in struct 'rkisp1_isp_mbus_info' that indicate
> + * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
>   * on which pad the media bus format is supported
>   */
>  #define RKISP1_ISP_SD_SRC			BIT(0)
> @@ -150,8 +150,8 @@ struct rkisp1_isp {
>  	struct v4l2_subdev sd;
>  	struct media_pad pads[RKISP1_ISP_PAD_MAX];
>  	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
> -	const struct rkisp1_isp_mbus_info *sink_fmt;
> -	const struct rkisp1_isp_mbus_info *src_fmt;
> +	const struct rkisp1_mbus_info *sink_fmt;
> +	const struct rkisp1_mbus_info *src_fmt;
>  	struct mutex ops_lock; /* serialize the subdevice ops */
>  	bool is_dphy_errctrl_disabled;
>  	__u32 frame_sequence;
> @@ -438,8 +438,8 @@ struct rkisp1_device {
>  };
>  
>  /*
> - * struct rkisp1_isp_mbus_info - ISP media bus info, Translates media bus code to hardware
> - *				 format values
> + * struct rkisp1_mbus_info - ISP media bus info, Translates media bus code to hardware
> + *			     format values
>   *
>   * @mbus_code: media bus code
>   * @pixel_enc: pixel encoding
> @@ -449,7 +449,7 @@ struct rkisp1_device {
>   * @bayer_pat: bayer pattern
>   * @direction: a bitmask of the flags indicating on which pad the format is supported on
>   */
> -struct rkisp1_isp_mbus_info {
> +struct rkisp1_mbus_info {
>  	u32 mbus_code;
>  	enum v4l2_pixel_encoding pixel_enc;
>  	u32 mipi_dt;
> @@ -481,6 +481,18 @@ static inline u32 rkisp1_read(struct rkisp1_device *rkisp1, unsigned int addr)
>  int rkisp1_cap_enum_mbus_codes(struct rkisp1_capture *cap,
>  			       struct v4l2_subdev_mbus_code_enum *code);
>  
> +/*
> + * rkisp1_mbus_info_length - Return the number of supported mbus codes
> + */
> +unsigned int rkisp1_mbus_info_length(void);
> +
> +/*
> + * rkisp1_mbus_info_get_by_index - Retrieve the ith supported mbus info
> + *
> + * @index: index of the mbus info to fetch
> + */
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index);
> +
>  /*
>   * rkisp1_sd_adjust_crop_rect - adjust a rectangle to fit into another rectangle.
>   *
> @@ -500,11 +512,11 @@ void rkisp1_sd_adjust_crop(struct v4l2_rect *crop,
>  			   const struct v4l2_mbus_framefmt *bounds);
>  
>  /*
> - * rkisp1_isp_mbus_info - get the isp info of the media bus code
> + * rkisp1_mbus_info_get_by_code - get the isp info of the media bus code
>   *
>   * @mbus_code: the media bus code
>   */
> -const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code);
> +const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code);
>  
>  /* rkisp1_params_configure - configure the params when stream starts.
>   *			     This function is called by the isp entity upon stream starts.
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> index 328e8fec14e9..89577119b571 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> @@ -15,7 +15,6 @@
>  #include <linux/videodev2.h>
>  #include <linux/vmalloc.h>
>  
> -#include <media/mipi-csi2.h>
>  #include <media/v4l2-event.h>
>  
>  #include "rkisp1-common.h"
> @@ -56,144 +55,10 @@
>   * +---------------------------------------------------------+
>   */
>  
> -static const struct rkisp1_isp_mbus_info rkisp1_isp_formats[] = {
> -	{
> -		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.direction	= RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_RGGB,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_BGGR,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_GBRG,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW10,
> -		.bayer_pat	= RKISP1_RAW_GRBG,
> -		.bus_width	= 10,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_RGGB,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_BGGR,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_GBRG,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW12,
> -		.bayer_pat	= RKISP1_RAW_GRBG,
> -		.bus_width	= 12,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_RGGB,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_BGGR,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_GBRG,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
> -		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
> -		.mipi_dt	= MIPI_CSI2_DT_RAW8,
> -		.bayer_pat	= RKISP1_RAW_GRBG,
> -		.bus_width	= 8,
> -		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	}, {
> -		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
> -		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
> -		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
> -		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
> -		.bus_width	= 16,
> -		.direction	= RKISP1_ISP_SD_SINK,
> -	},
> -};
> -
>  /* ----------------------------------------------------------------------------
>   * Helpers
>   */
>  
> -const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code)
> -{
> -	unsigned int i;
> -
> -	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
> -		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
> -
> -		if (fmt->mbus_code == mbus_code)
> -			return fmt;
> -	}
> -
> -	return NULL;
> -}
> -
>  static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
>  {
>  	struct media_pad *local, *remote;
> @@ -275,7 +140,7 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
>  static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>  {
>  	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
> -	const struct rkisp1_isp_mbus_info *src_fmt, *sink_fmt;
> +	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
>  	struct rkisp1_sensor_async *sensor;
>  	struct v4l2_mbus_framefmt *sink_frm;
>  	struct v4l2_rect *sink_crop;
> @@ -376,7 +241,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>  
>  static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>  {
> -	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> +	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>  	u32 val, input_sel;
>  
>  	switch (sink_fmt->bus_width) {
> @@ -402,7 +267,7 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>  
>  static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
>  {
> -	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> +	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>  	unsigned int lanes = rkisp1->active_sensor->lanes;
>  	u32 mipi_ctrl;
>  
> @@ -593,11 +458,12 @@ static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
>  		return 0;
>  	}
>  
> -	if (code->index >= ARRAY_SIZE(rkisp1_isp_formats))
> +	if (code->index >= rkisp1_mbus_info_length())
>  		return -EINVAL;
>  
> -	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
> -		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
> +	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
> +		const struct rkisp1_mbus_info *fmt =
> +			rkisp1_mbus_info_get_by_index(i);

You could write this as

	for (i = 0; ; i++) {
		const struct rkisp1_mbus_info *fmt =
			rkisp1_mbus_info_get_by_index(i);

		if (!fmt)
			return -EINVAL;

and drop the rkisp1_mbus_info_length() function. Up to you. Either way,

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

>  
>  		if (fmt->direction & dir)
>  			pos++;
> @@ -619,7 +485,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
>  				      struct v4l2_subdev_state *sd_state,
>  				      struct v4l2_subdev_frame_size_enum *fse)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  
>  	if (fse->pad == RKISP1_ISP_PAD_SINK_PARAMS ||
>  	    fse->pad == RKISP1_ISP_PAD_SOURCE_STATS)
> @@ -628,7 +494,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
>  	if (fse->index > 0)
>  		return -EINVAL;
>  
> -	mbus_info = rkisp1_isp_mbus_info_get(fse->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(fse->code);
>  	if (!mbus_info)
>  		return -EINVAL;
>  
> @@ -695,7 +561,7 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
>  				   struct v4l2_mbus_framefmt *format,
>  				   unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *src_fmt;
>  	const struct v4l2_rect *src_crop;
>  
> @@ -705,10 +571,10 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
>  					   RKISP1_ISP_PAD_SOURCE_VIDEO, which);
>  
>  	src_fmt->code = format->code;
> -	mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
>  	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
>  		src_fmt->code = RKISP1_DEF_SRC_PAD_FMT;
> -		mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
> +		mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
>  	}
>  	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
>  		isp->src_fmt = mbus_info;
> @@ -793,7 +659,7 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
>  				    struct v4l2_mbus_framefmt *format,
>  				    unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *sink_fmt;
>  	struct v4l2_rect *sink_crop;
>  
> @@ -801,10 +667,10 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
>  					  RKISP1_ISP_PAD_SINK_VIDEO,
>  					  which);
>  	sink_fmt->code = format->code;
> -	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
>  		sink_fmt->code = RKISP1_DEF_SINK_PAD_FMT;
> -		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	}
>  	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
>  		isp->sink_fmt = mbus_info;
> @@ -1080,8 +946,8 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
>  	pads[RKISP1_ISP_PAD_SOURCE_VIDEO].flags = MEDIA_PAD_FL_SOURCE;
>  	pads[RKISP1_ISP_PAD_SOURCE_STATS].flags = MEDIA_PAD_FL_SOURCE;
>  
> -	isp->sink_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SINK_PAD_FMT);
> -	isp->src_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SRC_PAD_FMT);
> +	isp->sink_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SINK_PAD_FMT);
> +	isp->src_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SRC_PAD_FMT);
>  
>  	mutex_init(&isp->ops_lock);
>  	ret = media_entity_pads_init(&sd->entity, RKISP1_ISP_PAD_MAX, pads);
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> index 1c07985c810d..f4caa8f684aa 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> @@ -433,14 +433,14 @@ static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
>  				   struct v4l2_mbus_framefmt *format,
>  				   unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *sink_mbus_info;
> +	const struct rkisp1_mbus_info *sink_mbus_info;
>  	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
>  
>  	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
>  					  which);
>  	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
>  					 which);
> -	sink_mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  
>  	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
>  	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
> @@ -462,7 +462,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
>  				     struct v4l2_rect *r,
>  				     unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *sink_fmt;
>  	struct v4l2_rect *sink_crop;
>  
> @@ -473,7 +473,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
>  					    which);
>  
>  	/* Not crop for MP bayer raw data */
> -	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  
>  	if (rsz->id == RKISP1_MAINPATH &&
>  	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
> @@ -500,7 +500,7 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
>  				    struct v4l2_mbus_framefmt *format,
>  				    unsigned int which)
>  {
> -	const struct rkisp1_isp_mbus_info *mbus_info;
> +	const struct rkisp1_mbus_info *mbus_info;
>  	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>  	struct v4l2_rect *sink_crop;
>  
> @@ -516,10 +516,10 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
>  	else
>  		sink_fmt->code = format->code;
>  
> -	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
>  		sink_fmt->code = RKISP1_DEF_FMT;
> -		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
> +		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>  	}
>  	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
>  		rsz->pixel_enc = mbus_info->pixel_enc;
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
> index 7d82356b5345..2795eef91bdd 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
> @@ -305,7 +305,7 @@ static void rkisp1_stats_get_bls_meas(struct rkisp1_stats *stats,
>  				      struct rkisp1_stat_buffer *pbuf)
>  {
>  	struct rkisp1_device *rkisp1 = stats->rkisp1;
> -	const struct rkisp1_isp_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
> +	const struct rkisp1_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
>  	struct rkisp1_cif_isp_bls_meas_val *bls_val;
>  
>  	bls_val = &pbuf->params.ae.bls_val;

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-16  7:32     ` Alexander Stein
  -1 siblings, 0 replies; 298+ messages in thread
From: Alexander Stein @ 2022-06-16  7:32 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello Paul,

Am Dienstag, 14. Juni 2022, 21:10:42 CEST schrieb Paul Elder:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> When a link validation failure occurs, print a debug message to help
> diagnosing the cause.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
>  1 file changed, 9 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c index
> 94819e6c23e2..94a0d787a312 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> @@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct
> media_link *link)
> 
>  	if (sd_fmt.format.height != cap->pix.fmt.height ||
>  	    sd_fmt.format.width != cap->pix.fmt.width ||
> -	    sd_fmt.format.code != fmt->mbus)
> +	    sd_fmt.format.code != fmt->mbus) {
> +		dev_dbg(cap->rkisp1->dev,

I wonder if a dev_warn is more suitable here.

Best regards,
Alexander

> +			"link '%s':%u -> '%s':%u not valid: 0x%04x/
%ux%u != 0x%04x/%ux%u",
> +			link->source->entity->name, link->source-
>index,
> +			link->sink->entity->name, link->sink->index,
> +			sd_fmt.format.code, sd_fmt.format.width,
> +			sd_fmt.format.height, fmt->mbus, cap-
>pix.fmt.width,
> +			cap->pix.fmt.height);
>  		return -EPIPE;
> +	}
> 
>  	return 0;
>  }





^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
@ 2022-06-16  7:32     ` Alexander Stein
  0 siblings, 0 replies; 298+ messages in thread
From: Alexander Stein @ 2022-06-16  7:32 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello Paul,

Am Dienstag, 14. Juni 2022, 21:10:42 CEST schrieb Paul Elder:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> When a link validation failure occurs, print a debug message to help
> diagnosing the cause.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
>  1 file changed, 9 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c index
> 94819e6c23e2..94a0d787a312 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> @@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct
> media_link *link)
> 
>  	if (sd_fmt.format.height != cap->pix.fmt.height ||
>  	    sd_fmt.format.width != cap->pix.fmt.width ||
> -	    sd_fmt.format.code != fmt->mbus)
> +	    sd_fmt.format.code != fmt->mbus) {
> +		dev_dbg(cap->rkisp1->dev,

I wonder if a dev_warn is more suitable here.

Best regards,
Alexander

> +			"link '%s':%u -> '%s':%u not valid: 0x%04x/
%ux%u != 0x%04x/%ux%u",
> +			link->source->entity->name, link->source-
>index,
> +			link->sink->entity->name, link->sink->index,
> +			sd_fmt.format.code, sd_fmt.format.width,
> +			sd_fmt.format.height, fmt->mbus, cap-
>pix.fmt.width,
> +			cap->pix.fmt.height);
>  		return -EPIPE;
> +	}
> 
>  	return 0;
>  }





_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
  2022-06-16  7:32     ` Alexander Stein
@ 2022-06-16  7:41       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  7:41 UTC (permalink / raw)
  To: Alexander Stein
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Alexander,

On Thu, Jun 16, 2022 at 09:32:17AM +0200, Alexander Stein wrote:
> Am Dienstag, 14. Juni 2022, 21:10:42 CEST schrieb Paul Elder:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > When a link validation failure occurs, print a debug message to help
> > diagnosing the cause.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
> >  1 file changed, 9 insertions(+), 1 deletion(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c index
> > 94819e6c23e2..94a0d787a312 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > @@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct
> > media_link *link)
> > 
> >  	if (sd_fmt.format.height != cap->pix.fmt.height ||
> >  	    sd_fmt.format.width != cap->pix.fmt.width ||
> > -	    sd_fmt.format.code != fmt->mbus)
> > +	    sd_fmt.format.code != fmt->mbus) {
> > +		dev_dbg(cap->rkisp1->dev,
> 
> I wonder if a dev_warn is more suitable here.

I usually recommend dev_dbg() for conditions that are triggered directly
by userspace, to avoid giving unpriviledged applications an(other) easy
way to flood the kernel log.

> > +			"link '%s':%u -> '%s':%u not valid: 0x%04x/ %ux%u != 0x%04x/%ux%u",
> > +			link->source->entity->name, link->source->index,
> > +			link->sink->entity->name, link->sink->index,
> > +			sd_fmt.format.code, sd_fmt.format.width,
> > +			sd_fmt.format.height, fmt->mbus, cap->pix.fmt.width,
> > +			cap->pix.fmt.height);
> >  		return -EPIPE;
> > +	}
> > 
> >  	return 0;
> >  }

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
@ 2022-06-16  7:41       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-16  7:41 UTC (permalink / raw)
  To: Alexander Stein
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Alexander,

On Thu, Jun 16, 2022 at 09:32:17AM +0200, Alexander Stein wrote:
> Am Dienstag, 14. Juni 2022, 21:10:42 CEST schrieb Paul Elder:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > When a link validation failure occurs, print a debug message to help
> > diagnosing the cause.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
> >  1 file changed, 9 insertions(+), 1 deletion(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c index
> > 94819e6c23e2..94a0d787a312 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > @@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct
> > media_link *link)
> > 
> >  	if (sd_fmt.format.height != cap->pix.fmt.height ||
> >  	    sd_fmt.format.width != cap->pix.fmt.width ||
> > -	    sd_fmt.format.code != fmt->mbus)
> > +	    sd_fmt.format.code != fmt->mbus) {
> > +		dev_dbg(cap->rkisp1->dev,
> 
> I wonder if a dev_warn is more suitable here.

I usually recommend dev_dbg() for conditions that are triggered directly
by userspace, to avoid giving unpriviledged applications an(other) easy
way to flood the kernel log.

> > +			"link '%s':%u -> '%s':%u not valid: 0x%04x/ %ux%u != 0x%04x/%ux%u",
> > +			link->source->entity->name, link->source->index,
> > +			link->sink->entity->name, link->sink->index,
> > +			sd_fmt.format.code, sd_fmt.format.width,
> > +			sd_fmt.format.height, fmt->mbus, cap->pix.fmt.width,
> > +			cap->pix.fmt.height);
> >  		return -EPIPE;
> > +	}
> > 
> >  	return 0;
> >  }

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) Re: (EXT) [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
  2022-06-16  7:41       ` Laurent Pinchart
@ 2022-06-16  7:59         ` Alexander Stein
  -1 siblings, 0 replies; 298+ messages in thread
From: Alexander Stein @ 2022-06-16  7:59 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello Laurent,

Am Donnerstag, 16. Juni 2022, 09:41:22 CEST schrieb Laurent Pinchart:
> Hi Alexander,
> 
> On Thu, Jun 16, 2022 at 09:32:17AM +0200, Alexander Stein wrote:
> > Am Dienstag, 14. Juni 2022, 21:10:42 CEST schrieb Paul Elder:
> > > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > 
> > > When a link validation failure occurs, print a debug message to help
> > > diagnosing the cause.
> > > 
> > > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > ---
> > > 
> > >  .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
> > >  1 file changed, 9 insertions(+), 1 deletion(-)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c index
> > > 94819e6c23e2..94a0d787a312 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > > @@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct
> > > media_link *link)
> > > 
> > >  	if (sd_fmt.format.height != cap->pix.fmt.height ||
> > >  	
> > >  	    sd_fmt.format.width != cap->pix.fmt.width ||
> > > 
> > > -	    sd_fmt.format.code != fmt->mbus)
> > > +	    sd_fmt.format.code != fmt->mbus) {
> > > +		dev_dbg(cap->rkisp1->dev,
> > 
> > I wonder if a dev_warn is more suitable here.
> 
> I usually recommend dev_dbg() for conditions that are triggered directly
> by userspace, to avoid giving unpriviledged applications an(other) easy
> way to flood the kernel log.

Agreed, this is a sensible thing to do. I'm still wondering if this 
information might be missing, when having a build without DYNAMIC_DEBUG.
Nevertheless I'm fine to start with this debug output at least.

Regards,
Alexander

> > > +			"link '%s':%u -> '%s':%u not valid: 0x%04x/ 
%ux%u != 0x%04x/%ux%u",
> > > +			link->source->entity->name, link->source-
>index,
> > > +			link->sink->entity->name, link->sink->index,
> > > +			sd_fmt.format.code, sd_fmt.format.width,
> > > +			sd_fmt.format.height, fmt->mbus, cap-
>pix.fmt.width,
> > > +			cap->pix.fmt.height);
> > > 
> > >  		return -EPIPE;
> > > 
> > > +	}
> > > 
> > >  	return 0;
> > >  
> > >  }





^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) Re: (EXT) [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
@ 2022-06-16  7:59         ` Alexander Stein
  0 siblings, 0 replies; 298+ messages in thread
From: Alexander Stein @ 2022-06-16  7:59 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello Laurent,

Am Donnerstag, 16. Juni 2022, 09:41:22 CEST schrieb Laurent Pinchart:
> Hi Alexander,
> 
> On Thu, Jun 16, 2022 at 09:32:17AM +0200, Alexander Stein wrote:
> > Am Dienstag, 14. Juni 2022, 21:10:42 CEST schrieb Paul Elder:
> > > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > 
> > > When a link validation failure occurs, print a debug message to help
> > > diagnosing the cause.
> > > 
> > > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > ---
> > > 
> > >  .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
> > >  1 file changed, 9 insertions(+), 1 deletion(-)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c index
> > > 94819e6c23e2..94a0d787a312 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> > > @@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct
> > > media_link *link)
> > > 
> > >  	if (sd_fmt.format.height != cap->pix.fmt.height ||
> > >  	
> > >  	    sd_fmt.format.width != cap->pix.fmt.width ||
> > > 
> > > -	    sd_fmt.format.code != fmt->mbus)
> > > +	    sd_fmt.format.code != fmt->mbus) {
> > > +		dev_dbg(cap->rkisp1->dev,
> > 
> > I wonder if a dev_warn is more suitable here.
> 
> I usually recommend dev_dbg() for conditions that are triggered directly
> by userspace, to avoid giving unpriviledged applications an(other) easy
> way to flood the kernel log.

Agreed, this is a sensible thing to do. I'm still wondering if this 
information might be missing, when having a build without DYNAMIC_DEBUG.
Nevertheless I'm fine to start with this debug output at least.

Regards,
Alexander

> > > +			"link '%s':%u -> '%s':%u not valid: 0x%04x/ 
%ux%u != 0x%04x/%ux%u",
> > > +			link->source->entity->name, link->source-
>index,
> > > +			link->sink->entity->name, link->sink->index,
> > > +			sd_fmt.format.code, sd_fmt.format.width,
> > > +			sd_fmt.format.height, fmt->mbus, cap-
>pix.fmt.width,
> > > +			cap->pix.fmt.height);
> > > 
> > >  		return -EPIPE;
> > > 
> > > +	}
> > > 
> > >  	return 0;
> > >  
> > >  }





_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-16  8:05     ` Alexander Stein
  -1 siblings, 0 replies; 298+ messages in thread
From: Alexander Stein @ 2022-06-16  8:05 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Paul Elder, dafna, heiko, laurent.pinchart,
	jeanmichel.hautbois, jacopo, djrscally, helen.koike,
	linux-rockchip

Hello Paul,

thanks for the patch.

Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> The ISP that is integrated in the i.MX8MP uses different bits in the
> MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> compared to the on in the RK3399. In addition, it adds a new bit for
> enabling crop. Add new definitions for these bits for i.MX8MP devices,
> and update where they are set.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
>  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
>  2 files changed, 12 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> 34f4fe09c88d..24ad2ccec2a3 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> @@ -168,6 +168,10 @@
>  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
>  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> 
> +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> +

Does it make sense to move this kind of information into struct rkisp1_info? 
This way you can skip the if (isp_ver == ...) thing.

Best regards,
Alexander

>  /* RSZ_CROP_[XY]_DIR */
>  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 
| (start) <<
> 0)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> 08bf3aa8088f..29a31b18a082 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> RKISP1_CIF_RSZ_CTRL);
> 
>  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> +			ctrl_cfg |= 
RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> +		else
> +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
>  	else
> -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> +		else
> +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> 
>  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
>  }





^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
@ 2022-06-16  8:05     ` Alexander Stein
  0 siblings, 0 replies; 298+ messages in thread
From: Alexander Stein @ 2022-06-16  8:05 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Paul Elder, dafna, heiko, laurent.pinchart,
	jeanmichel.hautbois, jacopo, djrscally, helen.koike,
	linux-rockchip

Hello Paul,

thanks for the patch.

Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> The ISP that is integrated in the i.MX8MP uses different bits in the
> MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> compared to the on in the RK3399. In addition, it adds a new bit for
> enabling crop. Add new definitions for these bits for i.MX8MP devices,
> and update where they are set.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
>  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
>  2 files changed, 12 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> 34f4fe09c88d..24ad2ccec2a3 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> @@ -168,6 +168,10 @@
>  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
>  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> 
> +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> +

Does it make sense to move this kind of information into struct rkisp1_info? 
This way you can skip the if (isp_ver == ...) thing.

Best regards,
Alexander

>  /* RSZ_CROP_[XY]_DIR */
>  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 
| (start) <<
> 0)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> 08bf3aa8088f..29a31b18a082 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> RKISP1_CIF_RSZ_CTRL);
> 
>  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> +			ctrl_cfg |= 
RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> +		else
> +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
>  	else
> -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> +		else
> +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> 
>  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
>  }





_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 11:38     ` Hans Verkuil
  -1 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-17 11:38 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip



On 6/14/22 21:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named

find -> finds

> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.
> 
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity

Shouldn't this be called media_entity_remote_source_pad_unique?

After all, it has the uniqueness constraint, but that's not reflected in the name.

With that change you can add my:

Acked-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

Regards,

	Hans

> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-17 11:38     ` Hans Verkuil
  0 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-17 11:38 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip



On 6/14/22 21:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named

find -> finds

> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.
> 
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity

Shouldn't this be called media_entity_remote_source_pad_unique?

After all, it has the uniqueness constraint, but that's not reflected in the name.

With that change you can add my:

Acked-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

Regards,

	Hans

> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 11:41     ` Hans Verkuil
  -1 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-17 11:41 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip



On 6/14/22 21:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The newly added media_entity_remote_source_pad() helper function handles
> use cases where the entity has a link enabled uniqueness constraint
> covering all pads. There are use cases where the constraint covers a
> specific pad only. Add a new media_pad_remote_pad() function to handle
> this. It operates as media_entity_remote_source_pad(), but on a given
> pad instead of on the entity.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +--
>  drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
>  include/media/media-entity.h               | 18 +++++++++++++
>  3 files changed, 51 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index a2d1e32e3abb..83c3bdbf67be 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> -:c:func:`media_entity_remote_source_pad()`).
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
> +:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 1febf5a86be6..6429b0510bfb 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>  
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
> +{
> +	struct media_pad *found_pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &pad->entity->links, list) {
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (link->sink == pad)
> +			remote_pad = link->source;
> +		else if (link->source == pad)
> +			remote_pad = link->sink;
> +		else
> +			continue;
> +
> +		if (found_pad)
> +			return ERR_PTR(-ENOTUNIQ);
> +
> +		found_pad = remote_pad;
> +	}
> +
> +	if (!found_pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return found_pad;
> +}
> +EXPORT_SYMBOL_GPL(media_pad_remote_pad);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index 33d5f52719a0..bfe6a7b10a68 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
>  	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>  }
>  
> +/**
> + * media_pad_remote_pad - Find a remote pad connected to a pad

Same question here: shouldn't this be called media_pad_remote_pad_unique?

> + * @pad: The pad
> + *
> + * Search for and return a remote pad connected to @pad through an enabled
> + * link. If multiple (or no) remote pads are found, an error is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time on a given pad.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

With that change:

Acked-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

Regards,

	Hans

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
@ 2022-06-17 11:41     ` Hans Verkuil
  0 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-17 11:41 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip



On 6/14/22 21:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The newly added media_entity_remote_source_pad() helper function handles
> use cases where the entity has a link enabled uniqueness constraint
> covering all pads. There are use cases where the constraint covers a
> specific pad only. Add a new media_pad_remote_pad() function to handle
> this. It operates as media_entity_remote_source_pad(), but on a given
> pad instead of on the entity.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +--
>  drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
>  include/media/media-entity.h               | 18 +++++++++++++
>  3 files changed, 51 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index a2d1e32e3abb..83c3bdbf67be 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> -:c:func:`media_entity_remote_source_pad()`).
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
> +:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 1febf5a86be6..6429b0510bfb 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>  
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
> +{
> +	struct media_pad *found_pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &pad->entity->links, list) {
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (link->sink == pad)
> +			remote_pad = link->source;
> +		else if (link->source == pad)
> +			remote_pad = link->sink;
> +		else
> +			continue;
> +
> +		if (found_pad)
> +			return ERR_PTR(-ENOTUNIQ);
> +
> +		found_pad = remote_pad;
> +	}
> +
> +	if (!found_pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return found_pad;
> +}
> +EXPORT_SYMBOL_GPL(media_pad_remote_pad);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index 33d5f52719a0..bfe6a7b10a68 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
>  	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>  }
>  
> +/**
> + * media_pad_remote_pad - Find a remote pad connected to a pad

Same question here: shouldn't this be called media_pad_remote_pad_unique?

> + * @pad: The pad
> + *
> + * Search for and return a remote pad connected to @pad through an enabled
> + * link. If multiple (or no) remote pads are found, an error is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time on a given pad.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

With that change:

Acked-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

Regards,

	Hans

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 11:48     ` Hans Verkuil
  -1 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-17 11:48 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip



On 6/14/22 21:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named
> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.

Question: of all the callers of this function, are there any that really
need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?

Would it be possible to replace all callers of the old function with the
new function? If that's the case, then the _unique suffix can be dropped,
since that would effectively be the default. And if a function is needed
to handle the case where there are multiple enabled links, then a new
function should be created.

Also, media_entity_remote_pad() should really be renamed to
media_pad_remote_pad_first() or something like that, right? I'm not saying
you should, but that's really what it does, as I understand it.

Regards,

	Hans

> 
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-17 11:48     ` Hans Verkuil
  0 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-17 11:48 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip



On 6/14/22 21:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named
> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.

Question: of all the callers of this function, are there any that really
need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?

Would it be possible to replace all callers of the old function with the
new function? If that's the case, then the _unique suffix can be dropped,
since that would effectively be the default. And if a function is needed
to handle the case where there are multiple enabled links, then a new
function should be created.

Also, media_entity_remote_pad() should really be renamed to
media_pad_remote_pad_first() or something like that, right? I'm not saying
you should, but that's really what it does, as I understand it.

Regards,

	Hans

> 
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
  2022-06-17 11:41     ` Hans Verkuil
@ 2022-06-17 11:48       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 11:48 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Fri, Jun 17, 2022 at 01:41:59PM +0200, Hans Verkuil wrote:
> On 6/14/22 21:11, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > The newly added media_entity_remote_source_pad() helper function handles
> > use cases where the entity has a link enabled uniqueness constraint
> > covering all pads. There are use cases where the constraint covers a
> > specific pad only. Add a new media_pad_remote_pad() function to handle
> > this. It operates as media_entity_remote_source_pad(), but on a given
> > pad instead of on the entity.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  Documentation/driver-api/media/mc-core.rst |  4 +--
> >  drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
> >  include/media/media-entity.h               | 18 +++++++++++++
> >  3 files changed, 51 insertions(+), 2 deletions(-)
> > 
> > diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> > index a2d1e32e3abb..83c3bdbf67be 100644
> > --- a/Documentation/driver-api/media/mc-core.rst
> > +++ b/Documentation/driver-api/media/mc-core.rst
> > @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >  
> >  Helper functions can be used to find a link between two given pads, or a pad
> >  connected to another pad through an enabled link
> > -(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> > -:c:func:`media_entity_remote_source_pad()`).
> > +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
> > +:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
> >  
> >  Use count and power handling
> >  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> > diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> > index 1febf5a86be6..6429b0510bfb 100644
> > --- a/drivers/media/mc/mc-entity.c
> > +++ b/drivers/media/mc/mc-entity.c
> > @@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
> >  }
> >  EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >  
> > +struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
> > +{
> > +	struct media_pad *found_pad = NULL;
> > +	struct media_link *link;
> > +
> > +	list_for_each_entry(link, &pad->entity->links, list) {
> > +		struct media_pad *remote_pad;
> > +
> > +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> > +			continue;
> > +
> > +		if (link->sink == pad)
> > +			remote_pad = link->source;
> > +		else if (link->source == pad)
> > +			remote_pad = link->sink;
> > +		else
> > +			continue;
> > +
> > +		if (found_pad)
> > +			return ERR_PTR(-ENOTUNIQ);
> > +
> > +		found_pad = remote_pad;
> > +	}
> > +
> > +	if (!found_pad)
> > +		return ERR_PTR(-ENOLINK);
> > +
> > +	return found_pad;
> > +}
> > +EXPORT_SYMBOL_GPL(media_pad_remote_pad);
> > +
> >  static void media_interface_init(struct media_device *mdev,
> >  				 struct media_interface *intf,
> >  				 u32 gobj_type,
> > diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> > index 33d5f52719a0..bfe6a7b10a68 100644
> > --- a/include/media/media-entity.h
> > +++ b/include/media/media-entity.h
> > @@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
> >  	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >  }
> >  
> > +/**
> > + * media_pad_remote_pad - Find a remote pad connected to a pad
> 
> Same question here: shouldn't this be called media_pad_remote_pad_unique?

I'm fine with that (and for the previous patch too). I'll wait for
Sakari's opinion and will then make the change.

> > + * @pad: The pad
> > + *
> > + * Search for and return a remote pad connected to @pad through an enabled
> > + * link. If multiple (or no) remote pads are found, an error is returned.
> > + *
> > + * The uniqueness constraint makes this helper function suitable for entities
> > + * that support a single active source at a time on a given pad.
> > + *
> > + * Return: A pointer to the remote pad, or one of the following error pointers
> > + * if an error occurs:
> > + *
> > + * * -ENOTUNIQ - Multiple links are enabled
> > + * * -ENOLINK - No connected pad found
> > + */
> > +struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
> > +
> >  /**
> >   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >   * @entity: The entity
> 
> With that change:
> 
> Acked-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad
@ 2022-06-17 11:48       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 11:48 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Fri, Jun 17, 2022 at 01:41:59PM +0200, Hans Verkuil wrote:
> On 6/14/22 21:11, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > The newly added media_entity_remote_source_pad() helper function handles
> > use cases where the entity has a link enabled uniqueness constraint
> > covering all pads. There are use cases where the constraint covers a
> > specific pad only. Add a new media_pad_remote_pad() function to handle
> > this. It operates as media_entity_remote_source_pad(), but on a given
> > pad instead of on the entity.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  Documentation/driver-api/media/mc-core.rst |  4 +--
> >  drivers/media/mc/mc-entity.c               | 31 ++++++++++++++++++++++
> >  include/media/media-entity.h               | 18 +++++++++++++
> >  3 files changed, 51 insertions(+), 2 deletions(-)
> > 
> > diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> > index a2d1e32e3abb..83c3bdbf67be 100644
> > --- a/Documentation/driver-api/media/mc-core.rst
> > +++ b/Documentation/driver-api/media/mc-core.rst
> > @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >  
> >  Helper functions can be used to find a link between two given pads, or a pad
> >  connected to another pad through an enabled link
> > -(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> > -:c:func:`media_entity_remote_source_pad()`).
> > +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()`,
> > +:c:func:`media_entity_remote_source_pad()` and :c:func:`media_pad_remote_pad()`).
> >  
> >  Use count and power handling
> >  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> > diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> > index 1febf5a86be6..6429b0510bfb 100644
> > --- a/drivers/media/mc/mc-entity.c
> > +++ b/drivers/media/mc/mc-entity.c
> > @@ -958,6 +958,37 @@ media_entity_remote_pad_unique(const struct media_entity *entity,
> >  }
> >  EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >  
> > +struct media_pad *media_pad_remote_pad(const struct media_pad *pad)
> > +{
> > +	struct media_pad *found_pad = NULL;
> > +	struct media_link *link;
> > +
> > +	list_for_each_entry(link, &pad->entity->links, list) {
> > +		struct media_pad *remote_pad;
> > +
> > +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> > +			continue;
> > +
> > +		if (link->sink == pad)
> > +			remote_pad = link->source;
> > +		else if (link->source == pad)
> > +			remote_pad = link->sink;
> > +		else
> > +			continue;
> > +
> > +		if (found_pad)
> > +			return ERR_PTR(-ENOTUNIQ);
> > +
> > +		found_pad = remote_pad;
> > +	}
> > +
> > +	if (!found_pad)
> > +		return ERR_PTR(-ENOLINK);
> > +
> > +	return found_pad;
> > +}
> > +EXPORT_SYMBOL_GPL(media_pad_remote_pad);
> > +
> >  static void media_interface_init(struct media_device *mdev,
> >  				 struct media_interface *intf,
> >  				 u32 gobj_type,
> > diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> > index 33d5f52719a0..bfe6a7b10a68 100644
> > --- a/include/media/media-entity.h
> > +++ b/include/media/media-entity.h
> > @@ -904,6 +904,24 @@ media_entity_remote_source_pad(const struct media_entity *entity)
> >  	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >  }
> >  
> > +/**
> > + * media_pad_remote_pad - Find a remote pad connected to a pad
> 
> Same question here: shouldn't this be called media_pad_remote_pad_unique?

I'm fine with that (and for the previous patch too). I'll wait for
Sakari's opinion and will then make the change.

> > + * @pad: The pad
> > + *
> > + * Search for and return a remote pad connected to @pad through an enabled
> > + * link. If multiple (or no) remote pads are found, an error is returned.
> > + *
> > + * The uniqueness constraint makes this helper function suitable for entities
> > + * that support a single active source at a time on a given pad.
> > + *
> > + * Return: A pointer to the remote pad, or one of the following error pointers
> > + * if an error occurs:
> > + *
> > + * * -ENOTUNIQ - Multiple links are enabled
> > + * * -ENOLINK - No connected pad found
> > + */
> > +struct media_pad *media_pad_remote_pad(const struct media_pad *pad);
> > +
> >  /**
> >   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >   * @entity: The entity
> 
> With that change:
> 
> Acked-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 21:34     ` Daniel Scally
  -1 siblings, 0 replies; 298+ messages in thread
From: Daniel Scally @ 2022-06-17 21:34 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	helen.koike, linux-rockchip

Hello all

On 14/06/2022 20:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named
> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.
>
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
>
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
>
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
Does this need another guard here to make sure the link isn't an
ancillary link? Only likely to happen at least in the immediate future
where the entity represents a camera sensor, so possibly not applicable
here - I couldn't find where the new function is used in the series to
check. I _think_ it would actually work ok regardless...media_gobj
type-punning makes my brain ache, but I think the local_pad->entity ==
entity comparison would actually compare the entity->name member of the
entity at the end of an ancillary link to the entity parameter, not find
a match and so continue the loop without failing, but that feels a bit
sub-optimal.



> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-17 21:34     ` Daniel Scally
  0 siblings, 0 replies; 298+ messages in thread
From: Daniel Scally @ 2022-06-17 21:34 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	helen.koike, linux-rockchip

Hello all

On 14/06/2022 20:11, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
> The media_entity_remote_pad() helper function returns the first remote
> pad it find connected to a given pad. Beside being possibly ill-named
> (as it operates on a pad, not an entity) and non-deterministic (as it
> stops at the first enabled link), the fact that it returns the first
> match makes it unsuitable for drivers that need to guarantee that a
> single link is enabled, for instance when an entity can process data
> from one of multiple sources at a time.
>
> For those use cases, add a new helper function,
> media_entity_remote_pad_unique(), that operates on an entity and returns
> a remote pad, with a guarantee that only one link is enabled. To ease
> its use in drivers, also add an inline wrapper that locates source pads
> specifically. A wrapper that locates sink pads can easily be added when
> needed.
>
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> ---
>  Documentation/driver-api/media/mc-core.rst |  4 +-
>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>  3 files changed, 85 insertions(+), 2 deletions(-)
>
> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> index 02481a2513b9..a2d1e32e3abb 100644
> --- a/Documentation/driver-api/media/mc-core.rst
> +++ b/Documentation/driver-api/media/mc-core.rst
> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>  
>  Helper functions can be used to find a link between two given pads, or a pad
>  connected to another pad through an enabled link
> -:c:func:`media_entity_find_link()` and
> -:c:func:`media_entity_remote_pad()`.
> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> +:c:func:`media_entity_remote_source_pad()`).
>  
>  Use count and power handling
>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> index 11f5207f73aa..1febf5a86be6 100644
> --- a/drivers/media/mc/mc-entity.c
> +++ b/drivers/media/mc/mc-entity.c
> @@ -9,6 +9,7 @@
>   */
>  
>  #include <linux/bitmap.h>
> +#include <linux/list.h>
>  #include <linux/property.h>
>  #include <linux/slab.h>
>  #include <media/media-entity.h>
> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>  }
>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>  
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type)
> +{
> +	struct media_pad *pad = NULL;
> +	struct media_link *link;
> +
> +	list_for_each_entry(link, &entity->links, list) {
> +		struct media_pad *local_pad;
> +		struct media_pad *remote_pad;
> +
> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> +			continue;
Does this need another guard here to make sure the link isn't an
ancillary link? Only likely to happen at least in the immediate future
where the entity represents a camera sensor, so possibly not applicable
here - I couldn't find where the new function is used in the series to
check. I _think_ it would actually work ok regardless...media_gobj
type-punning makes my brain ache, but I think the local_pad->entity ==
entity comparison would actually compare the entity->name member of the
entity at the end of an ancillary link to the entity parameter, not find
a match and so continue the loop without failing, but that feels a bit
sub-optimal.



> +
> +		if (type == MEDIA_PAD_FL_SOURCE) {
> +			local_pad = link->sink;
> +			remote_pad = link->source;
> +		} else {
> +			local_pad = link->source;
> +			remote_pad = link->sink;
> +		}
> +
> +		if (local_pad->entity == entity) {
> +			if (pad)
> +				return ERR_PTR(-ENOTUNIQ);
> +
> +			pad = remote_pad;
> +		}
> +	}
> +
> +	if (!pad)
> +		return ERR_PTR(-ENOLINK);
> +
> +	return pad;
> +}
> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> +
>  static void media_interface_init(struct media_device *mdev,
>  				 struct media_interface *intf,
>  				 u32 gobj_type,
> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> index a9a1c0ec5d1c..33d5f52719a0 100644
> --- a/include/media/media-entity.h
> +++ b/include/media/media-entity.h
> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>   */
>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>  
> +/**
> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> + * @entity: The entity
> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> + *
> + * Search for and return a remote pad of @type connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source or sink at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +struct media_pad *
> +media_entity_remote_pad_unique(const struct media_entity *entity,
> +			       unsigned int type);
> +
> +/**
> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> + * @entity: The entity
> + *
> + * Search for and return a remote source pad connected to @entity through an
> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> + * is returned.
> + *
> + * The uniqueness constraint makes this helper function suitable for entities
> + * that support a single active source at a time.
> + *
> + * Return: A pointer to the remote pad, or one of the following error pointers
> + * if an error occurs:
> + *
> + * * -ENOTUNIQ - Multiple links are enabled
> + * * -ENOLINK - No connected pad found
> + */
> +static inline struct media_pad *
> +media_entity_remote_source_pad(const struct media_entity *entity)
> +{
> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> +}
> +
>  /**
>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>   * @entity: The entity

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-17 21:34     ` Daniel Scally
@ 2022-06-17 22:33       ` Daniel Scally
  -1 siblings, 0 replies; 298+ messages in thread
From: Daniel Scally @ 2022-06-17 22:33 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	helen.koike, linux-rockchip


On 17/06/2022 22:34, Daniel Scally wrote:
> Hello all
>
> On 14/06/2022 20:11, Paul Elder wrote:
>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>
>> The media_entity_remote_pad() helper function returns the first remote
>> pad it find connected to a given pad. Beside being possibly ill-named
>> (as it operates on a pad, not an entity) and non-deterministic (as it
>> stops at the first enabled link), the fact that it returns the first
>> match makes it unsuitable for drivers that need to guarantee that a
>> single link is enabled, for instance when an entity can process data
>> from one of multiple sources at a time.
>>
>> For those use cases, add a new helper function,
>> media_entity_remote_pad_unique(), that operates on an entity and returns
>> a remote pad, with a guarantee that only one link is enabled. To ease
>> its use in drivers, also add an inline wrapper that locates source pads
>> specifically. A wrapper that locates sink pads can easily be added when
>> needed.
>>
>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>> ---
>>  Documentation/driver-api/media/mc-core.rst |  4 +-
>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>>  3 files changed, 85 insertions(+), 2 deletions(-)
>>
>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
>> index 02481a2513b9..a2d1e32e3abb 100644
>> --- a/Documentation/driver-api/media/mc-core.rst
>> +++ b/Documentation/driver-api/media/mc-core.rst
>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>>  
>>  Helper functions can be used to find a link between two given pads, or a pad
>>  connected to another pad through an enabled link
>> -:c:func:`media_entity_find_link()` and
>> -:c:func:`media_entity_remote_pad()`.
>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
>> +:c:func:`media_entity_remote_source_pad()`).
>>  
>>  Use count and power handling
>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
>> index 11f5207f73aa..1febf5a86be6 100644
>> --- a/drivers/media/mc/mc-entity.c
>> +++ b/drivers/media/mc/mc-entity.c
>> @@ -9,6 +9,7 @@
>>   */
>>  
>>  #include <linux/bitmap.h>
>> +#include <linux/list.h>
>>  #include <linux/property.h>
>>  #include <linux/slab.h>
>>  #include <media/media-entity.h>
>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>>  }
>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>>  
>> +struct media_pad *
>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>> +			       unsigned int type)
>> +{
>> +	struct media_pad *pad = NULL;
>> +	struct media_link *link;
>> +
>> +	list_for_each_entry(link, &entity->links, list) {
>> +		struct media_pad *local_pad;
>> +		struct media_pad *remote_pad;
>> +
>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
>> +			continue;
> Does this need another guard here to make sure the link isn't an
> ancillary link? Only likely to happen at least in the immediate future
> where the entity represents a camera sensor, so possibly not applicable
> here - I couldn't find where the new function is used in the series to
> check. I _think_ it would actually work ok regardless...media_gobj
> type-punning makes my brain ache, but I think the local_pad->entity ==
> entity comparison would actually compare the entity->name member of the
> entity at the end of an ancillary link to the entity parameter, not find
> a match and so continue the loop without failing, but that feels a bit
> sub-optimal.
>

Or perhaps a better approach would be to provide something like a
"list_for_each_data_link()" iterator - the potential problem here (as
with Quentin's recent issue with the rkisp1 driver) is the assumption
that all links are data links, so maybe it's best to just guarantee that
if we can.

>
>> +
>> +		if (type == MEDIA_PAD_FL_SOURCE) {
>> +			local_pad = link->sink;
>> +			remote_pad = link->source;
>> +		} else {
>> +			local_pad = link->source;
>> +			remote_pad = link->sink;
>> +		}
>> +
>> +		if (local_pad->entity == entity) {
>> +			if (pad)
>> +				return ERR_PTR(-ENOTUNIQ);
>> +
>> +			pad = remote_pad;
>> +		}
>> +	}
>> +
>> +	if (!pad)
>> +		return ERR_PTR(-ENOLINK);
>> +
>> +	return pad;
>> +}
>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>> +
>>  static void media_interface_init(struct media_device *mdev,
>>  				 struct media_interface *intf,
>>  				 u32 gobj_type,
>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
>> index a9a1c0ec5d1c..33d5f52719a0 100644
>> --- a/include/media/media-entity.h
>> +++ b/include/media/media-entity.h
>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>>   */
>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>>  
>> +/**
>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
>> + * @entity: The entity
>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
>> + *
>> + * Search for and return a remote pad of @type connected to @entity through an
>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>> + * is returned.
>> + *
>> + * The uniqueness constraint makes this helper function suitable for entities
>> + * that support a single active source or sink at a time.
>> + *
>> + * Return: A pointer to the remote pad, or one of the following error pointers
>> + * if an error occurs:
>> + *
>> + * * -ENOTUNIQ - Multiple links are enabled
>> + * * -ENOLINK - No connected pad found
>> + */
>> +struct media_pad *
>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>> +			       unsigned int type);
>> +
>> +/**
>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
>> + * @entity: The entity
>> + *
>> + * Search for and return a remote source pad connected to @entity through an
>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>> + * is returned.
>> + *
>> + * The uniqueness constraint makes this helper function suitable for entities
>> + * that support a single active source at a time.
>> + *
>> + * Return: A pointer to the remote pad, or one of the following error pointers
>> + * if an error occurs:
>> + *
>> + * * -ENOTUNIQ - Multiple links are enabled
>> + * * -ENOLINK - No connected pad found
>> + */
>> +static inline struct media_pad *
>> +media_entity_remote_source_pad(const struct media_entity *entity)
>> +{
>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>> +}
>> +
>>  /**
>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>>   * @entity: The entity

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-17 22:33       ` Daniel Scally
  0 siblings, 0 replies; 298+ messages in thread
From: Daniel Scally @ 2022-06-17 22:33 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	helen.koike, linux-rockchip


On 17/06/2022 22:34, Daniel Scally wrote:
> Hello all
>
> On 14/06/2022 20:11, Paul Elder wrote:
>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>
>> The media_entity_remote_pad() helper function returns the first remote
>> pad it find connected to a given pad. Beside being possibly ill-named
>> (as it operates on a pad, not an entity) and non-deterministic (as it
>> stops at the first enabled link), the fact that it returns the first
>> match makes it unsuitable for drivers that need to guarantee that a
>> single link is enabled, for instance when an entity can process data
>> from one of multiple sources at a time.
>>
>> For those use cases, add a new helper function,
>> media_entity_remote_pad_unique(), that operates on an entity and returns
>> a remote pad, with a guarantee that only one link is enabled. To ease
>> its use in drivers, also add an inline wrapper that locates source pads
>> specifically. A wrapper that locates sink pads can easily be added when
>> needed.
>>
>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>> ---
>>  Documentation/driver-api/media/mc-core.rst |  4 +-
>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>>  3 files changed, 85 insertions(+), 2 deletions(-)
>>
>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
>> index 02481a2513b9..a2d1e32e3abb 100644
>> --- a/Documentation/driver-api/media/mc-core.rst
>> +++ b/Documentation/driver-api/media/mc-core.rst
>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>>  
>>  Helper functions can be used to find a link between two given pads, or a pad
>>  connected to another pad through an enabled link
>> -:c:func:`media_entity_find_link()` and
>> -:c:func:`media_entity_remote_pad()`.
>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
>> +:c:func:`media_entity_remote_source_pad()`).
>>  
>>  Use count and power handling
>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
>> index 11f5207f73aa..1febf5a86be6 100644
>> --- a/drivers/media/mc/mc-entity.c
>> +++ b/drivers/media/mc/mc-entity.c
>> @@ -9,6 +9,7 @@
>>   */
>>  
>>  #include <linux/bitmap.h>
>> +#include <linux/list.h>
>>  #include <linux/property.h>
>>  #include <linux/slab.h>
>>  #include <media/media-entity.h>
>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>>  }
>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>>  
>> +struct media_pad *
>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>> +			       unsigned int type)
>> +{
>> +	struct media_pad *pad = NULL;
>> +	struct media_link *link;
>> +
>> +	list_for_each_entry(link, &entity->links, list) {
>> +		struct media_pad *local_pad;
>> +		struct media_pad *remote_pad;
>> +
>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
>> +			continue;
> Does this need another guard here to make sure the link isn't an
> ancillary link? Only likely to happen at least in the immediate future
> where the entity represents a camera sensor, so possibly not applicable
> here - I couldn't find where the new function is used in the series to
> check. I _think_ it would actually work ok regardless...media_gobj
> type-punning makes my brain ache, but I think the local_pad->entity ==
> entity comparison would actually compare the entity->name member of the
> entity at the end of an ancillary link to the entity parameter, not find
> a match and so continue the loop without failing, but that feels a bit
> sub-optimal.
>

Or perhaps a better approach would be to provide something like a
"list_for_each_data_link()" iterator - the potential problem here (as
with Quentin's recent issue with the rkisp1 driver) is the assumption
that all links are data links, so maybe it's best to just guarantee that
if we can.

>
>> +
>> +		if (type == MEDIA_PAD_FL_SOURCE) {
>> +			local_pad = link->sink;
>> +			remote_pad = link->source;
>> +		} else {
>> +			local_pad = link->source;
>> +			remote_pad = link->sink;
>> +		}
>> +
>> +		if (local_pad->entity == entity) {
>> +			if (pad)
>> +				return ERR_PTR(-ENOTUNIQ);
>> +
>> +			pad = remote_pad;
>> +		}
>> +	}
>> +
>> +	if (!pad)
>> +		return ERR_PTR(-ENOLINK);
>> +
>> +	return pad;
>> +}
>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>> +
>>  static void media_interface_init(struct media_device *mdev,
>>  				 struct media_interface *intf,
>>  				 u32 gobj_type,
>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
>> index a9a1c0ec5d1c..33d5f52719a0 100644
>> --- a/include/media/media-entity.h
>> +++ b/include/media/media-entity.h
>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>>   */
>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>>  
>> +/**
>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
>> + * @entity: The entity
>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
>> + *
>> + * Search for and return a remote pad of @type connected to @entity through an
>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>> + * is returned.
>> + *
>> + * The uniqueness constraint makes this helper function suitable for entities
>> + * that support a single active source or sink at a time.
>> + *
>> + * Return: A pointer to the remote pad, or one of the following error pointers
>> + * if an error occurs:
>> + *
>> + * * -ENOTUNIQ - Multiple links are enabled
>> + * * -ENOLINK - No connected pad found
>> + */
>> +struct media_pad *
>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>> +			       unsigned int type);
>> +
>> +/**
>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
>> + * @entity: The entity
>> + *
>> + * Search for and return a remote source pad connected to @entity through an
>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>> + * is returned.
>> + *
>> + * The uniqueness constraint makes this helper function suitable for entities
>> + * that support a single active source at a time.
>> + *
>> + * Return: A pointer to the remote pad, or one of the following error pointers
>> + * if an error occurs:
>> + *
>> + * * -ENOTUNIQ - Multiple links are enabled
>> + * * -ENOLINK - No connected pad found
>> + */
>> +static inline struct media_pad *
>> +media_entity_remote_source_pad(const struct media_entity *entity)
>> +{
>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>> +}
>> +
>>  /**
>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>>   * @entity: The entity

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-17 22:33       ` Daniel Scally
@ 2022-06-17 22:40         ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 22:40 UTC (permalink / raw)
  To: Daniel Scally
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, helen.koike, linux-rockchip

Hi Daniel,

On Fri, Jun 17, 2022 at 11:33:03PM +0100, Daniel Scally wrote:
> On 17/06/2022 22:34, Daniel Scally wrote:
> > On 14/06/2022 20:11, Paul Elder wrote:
> >> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>
> >> The media_entity_remote_pad() helper function returns the first remote
> >> pad it find connected to a given pad. Beside being possibly ill-named
> >> (as it operates on a pad, not an entity) and non-deterministic (as it
> >> stops at the first enabled link), the fact that it returns the first
> >> match makes it unsuitable for drivers that need to guarantee that a
> >> single link is enabled, for instance when an entity can process data
> >> from one of multiple sources at a time.
> >>
> >> For those use cases, add a new helper function,
> >> media_entity_remote_pad_unique(), that operates on an entity and returns
> >> a remote pad, with a guarantee that only one link is enabled. To ease
> >> its use in drivers, also add an inline wrapper that locates source pads
> >> specifically. A wrapper that locates sink pads can easily be added when
> >> needed.
> >>
> >> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >> ---
> >>  Documentation/driver-api/media/mc-core.rst |  4 +-
> >>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >>  3 files changed, 85 insertions(+), 2 deletions(-)
> >>
> >> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> >> index 02481a2513b9..a2d1e32e3abb 100644
> >> --- a/Documentation/driver-api/media/mc-core.rst
> >> +++ b/Documentation/driver-api/media/mc-core.rst
> >> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >>  
> >>  Helper functions can be used to find a link between two given pads, or a pad
> >>  connected to another pad through an enabled link
> >> -:c:func:`media_entity_find_link()` and
> >> -:c:func:`media_entity_remote_pad()`.
> >> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> >> +:c:func:`media_entity_remote_source_pad()`).
> >>  
> >>  Use count and power handling
> >>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> >> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> >> index 11f5207f73aa..1febf5a86be6 100644
> >> --- a/drivers/media/mc/mc-entity.c
> >> +++ b/drivers/media/mc/mc-entity.c
> >> @@ -9,6 +9,7 @@
> >>   */
> >>  
> >>  #include <linux/bitmap.h>
> >> +#include <linux/list.h>
> >>  #include <linux/property.h>
> >>  #include <linux/slab.h>
> >>  #include <media/media-entity.h>
> >> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >>  }
> >>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >>  
> >> +struct media_pad *
> >> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >> +			       unsigned int type)
> >> +{
> >> +	struct media_pad *pad = NULL;
> >> +	struct media_link *link;
> >> +
> >> +	list_for_each_entry(link, &entity->links, list) {
> >> +		struct media_pad *local_pad;
> >> +		struct media_pad *remote_pad;
> >> +
> >> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> >> +			continue;
> > 
> > Does this need another guard here to make sure the link isn't an
> > ancillary link? Only likely to happen at least in the immediate future
> > where the entity represents a camera sensor, so possibly not applicable
> > here - I couldn't find where the new function is used in the series to
> > check. I _think_ it would actually work ok regardless...media_gobj
> > type-punning makes my brain ache, but I think the local_pad->entity ==
> > entity comparison would actually compare the entity->name member of the
> > entity at the end of an ancillary link to the entity parameter, not find
> > a match and so continue the loop without failing, but that feels a bit
> > sub-optimal.
> 
> Or perhaps a better approach would be to provide something like a
> "list_for_each_data_link()" iterator - the potential problem here (as
> with Quentin's recent issue with the rkisp1 driver) is the assumption
> that all links are data links, so maybe it's best to just guarantee that
> if we can.

I agree with you, without a dedicated iterator, we're bound to repeat
the mistake over and over.

Would you like to submit a patch to add that iterator, or should I ? I'd
name it for_each_media_entity_data_link() or something similar.

> >> +
> >> +		if (type == MEDIA_PAD_FL_SOURCE) {
> >> +			local_pad = link->sink;
> >> +			remote_pad = link->source;
> >> +		} else {
> >> +			local_pad = link->source;
> >> +			remote_pad = link->sink;
> >> +		}
> >> +
> >> +		if (local_pad->entity == entity) {
> >> +			if (pad)
> >> +				return ERR_PTR(-ENOTUNIQ);
> >> +
> >> +			pad = remote_pad;
> >> +		}
> >> +	}
> >> +
> >> +	if (!pad)
> >> +		return ERR_PTR(-ENOLINK);
> >> +
> >> +	return pad;
> >> +}
> >> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >> +
> >>  static void media_interface_init(struct media_device *mdev,
> >>  				 struct media_interface *intf,
> >>  				 u32 gobj_type,
> >> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> >> index a9a1c0ec5d1c..33d5f52719a0 100644
> >> --- a/include/media/media-entity.h
> >> +++ b/include/media/media-entity.h
> >> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >>   */
> >>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >>  
> >> +/**
> >> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> >> + * @entity: The entity
> >> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> >> + *
> >> + * Search for and return a remote pad of @type connected to @entity through an
> >> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >> + * is returned.
> >> + *
> >> + * The uniqueness constraint makes this helper function suitable for entities
> >> + * that support a single active source or sink at a time.
> >> + *
> >> + * Return: A pointer to the remote pad, or one of the following error pointers
> >> + * if an error occurs:
> >> + *
> >> + * * -ENOTUNIQ - Multiple links are enabled
> >> + * * -ENOLINK - No connected pad found
> >> + */
> >> +struct media_pad *
> >> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >> +			       unsigned int type);
> >> +
> >> +/**
> >> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> >> + * @entity: The entity
> >> + *
> >> + * Search for and return a remote source pad connected to @entity through an
> >> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >> + * is returned.
> >> + *
> >> + * The uniqueness constraint makes this helper function suitable for entities
> >> + * that support a single active source at a time.
> >> + *
> >> + * Return: A pointer to the remote pad, or one of the following error pointers
> >> + * if an error occurs:
> >> + *
> >> + * * -ENOTUNIQ - Multiple links are enabled
> >> + * * -ENOLINK - No connected pad found
> >> + */
> >> +static inline struct media_pad *
> >> +media_entity_remote_source_pad(const struct media_entity *entity)
> >> +{
> >> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >> +}
> >> +
> >>  /**
> >>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >>   * @entity: The entity

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-17 22:40         ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 22:40 UTC (permalink / raw)
  To: Daniel Scally
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, helen.koike, linux-rockchip

Hi Daniel,

On Fri, Jun 17, 2022 at 11:33:03PM +0100, Daniel Scally wrote:
> On 17/06/2022 22:34, Daniel Scally wrote:
> > On 14/06/2022 20:11, Paul Elder wrote:
> >> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>
> >> The media_entity_remote_pad() helper function returns the first remote
> >> pad it find connected to a given pad. Beside being possibly ill-named
> >> (as it operates on a pad, not an entity) and non-deterministic (as it
> >> stops at the first enabled link), the fact that it returns the first
> >> match makes it unsuitable for drivers that need to guarantee that a
> >> single link is enabled, for instance when an entity can process data
> >> from one of multiple sources at a time.
> >>
> >> For those use cases, add a new helper function,
> >> media_entity_remote_pad_unique(), that operates on an entity and returns
> >> a remote pad, with a guarantee that only one link is enabled. To ease
> >> its use in drivers, also add an inline wrapper that locates source pads
> >> specifically. A wrapper that locates sink pads can easily be added when
> >> needed.
> >>
> >> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >> ---
> >>  Documentation/driver-api/media/mc-core.rst |  4 +-
> >>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >>  3 files changed, 85 insertions(+), 2 deletions(-)
> >>
> >> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> >> index 02481a2513b9..a2d1e32e3abb 100644
> >> --- a/Documentation/driver-api/media/mc-core.rst
> >> +++ b/Documentation/driver-api/media/mc-core.rst
> >> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >>  
> >>  Helper functions can be used to find a link between two given pads, or a pad
> >>  connected to another pad through an enabled link
> >> -:c:func:`media_entity_find_link()` and
> >> -:c:func:`media_entity_remote_pad()`.
> >> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> >> +:c:func:`media_entity_remote_source_pad()`).
> >>  
> >>  Use count and power handling
> >>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> >> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> >> index 11f5207f73aa..1febf5a86be6 100644
> >> --- a/drivers/media/mc/mc-entity.c
> >> +++ b/drivers/media/mc/mc-entity.c
> >> @@ -9,6 +9,7 @@
> >>   */
> >>  
> >>  #include <linux/bitmap.h>
> >> +#include <linux/list.h>
> >>  #include <linux/property.h>
> >>  #include <linux/slab.h>
> >>  #include <media/media-entity.h>
> >> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >>  }
> >>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >>  
> >> +struct media_pad *
> >> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >> +			       unsigned int type)
> >> +{
> >> +	struct media_pad *pad = NULL;
> >> +	struct media_link *link;
> >> +
> >> +	list_for_each_entry(link, &entity->links, list) {
> >> +		struct media_pad *local_pad;
> >> +		struct media_pad *remote_pad;
> >> +
> >> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> >> +			continue;
> > 
> > Does this need another guard here to make sure the link isn't an
> > ancillary link? Only likely to happen at least in the immediate future
> > where the entity represents a camera sensor, so possibly not applicable
> > here - I couldn't find where the new function is used in the series to
> > check. I _think_ it would actually work ok regardless...media_gobj
> > type-punning makes my brain ache, but I think the local_pad->entity ==
> > entity comparison would actually compare the entity->name member of the
> > entity at the end of an ancillary link to the entity parameter, not find
> > a match and so continue the loop without failing, but that feels a bit
> > sub-optimal.
> 
> Or perhaps a better approach would be to provide something like a
> "list_for_each_data_link()" iterator - the potential problem here (as
> with Quentin's recent issue with the rkisp1 driver) is the assumption
> that all links are data links, so maybe it's best to just guarantee that
> if we can.

I agree with you, without a dedicated iterator, we're bound to repeat
the mistake over and over.

Would you like to submit a patch to add that iterator, or should I ? I'd
name it for_each_media_entity_data_link() or something similar.

> >> +
> >> +		if (type == MEDIA_PAD_FL_SOURCE) {
> >> +			local_pad = link->sink;
> >> +			remote_pad = link->source;
> >> +		} else {
> >> +			local_pad = link->source;
> >> +			remote_pad = link->sink;
> >> +		}
> >> +
> >> +		if (local_pad->entity == entity) {
> >> +			if (pad)
> >> +				return ERR_PTR(-ENOTUNIQ);
> >> +
> >> +			pad = remote_pad;
> >> +		}
> >> +	}
> >> +
> >> +	if (!pad)
> >> +		return ERR_PTR(-ENOLINK);
> >> +
> >> +	return pad;
> >> +}
> >> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >> +
> >>  static void media_interface_init(struct media_device *mdev,
> >>  				 struct media_interface *intf,
> >>  				 u32 gobj_type,
> >> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> >> index a9a1c0ec5d1c..33d5f52719a0 100644
> >> --- a/include/media/media-entity.h
> >> +++ b/include/media/media-entity.h
> >> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >>   */
> >>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >>  
> >> +/**
> >> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> >> + * @entity: The entity
> >> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> >> + *
> >> + * Search for and return a remote pad of @type connected to @entity through an
> >> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >> + * is returned.
> >> + *
> >> + * The uniqueness constraint makes this helper function suitable for entities
> >> + * that support a single active source or sink at a time.
> >> + *
> >> + * Return: A pointer to the remote pad, or one of the following error pointers
> >> + * if an error occurs:
> >> + *
> >> + * * -ENOTUNIQ - Multiple links are enabled
> >> + * * -ENOLINK - No connected pad found
> >> + */
> >> +struct media_pad *
> >> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >> +			       unsigned int type);
> >> +
> >> +/**
> >> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> >> + * @entity: The entity
> >> + *
> >> + * Search for and return a remote source pad connected to @entity through an
> >> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >> + * is returned.
> >> + *
> >> + * The uniqueness constraint makes this helper function suitable for entities
> >> + * that support a single active source at a time.
> >> + *
> >> + * Return: A pointer to the remote pad, or one of the following error pointers
> >> + * if an error occurs:
> >> + *
> >> + * * -ENOTUNIQ - Multiple links are enabled
> >> + * * -ENOLINK - No connected pad found
> >> + */
> >> +static inline struct media_pad *
> >> +media_entity_remote_source_pad(const struct media_entity *entity)
> >> +{
> >> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >> +}
> >> +
> >>  /**
> >>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >>   * @entity: The entity

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 42/55] media: rkisp1: Use fwnode_graph_for_each_endpoint
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 22:56     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 22:56 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:14AM +0900, Paul Elder wrote:
> When registering the notifier, replace the manual while loop with
> fwnode_graph_for_each_endpoint. This simplifies error handling.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 44 +++++++++----------
>  1 file changed, 20 insertions(+), 24 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index a3e182c86bdd..00ace8224575 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -158,29 +158,28 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
>  static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>  {
>  	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
> -	unsigned int next_id = 0;
> +	struct fwnode_handle *fwnode = dev_fwnode(rkisp1->dev);
> +	struct fwnode_handle *ep;
>  	unsigned int index = 0;
> -	int ret;
> +	int ret = 0;
>  
>  	v4l2_async_nf_init(ntf);
>  
> -	while (1) {
> +	ntf->ops = &rkisp1_subdev_notifier_ops;
> +
> +	fwnode_graph_for_each_endpoint(fwnode, ep) {
>  		struct v4l2_fwnode_endpoint vep = {
>  			.bus_type = V4L2_MBUS_CSI2_DPHY
>  		};
>  		struct rkisp1_sensor_async *rk_asd;
> -		struct fwnode_handle *source = NULL;
> -		struct fwnode_handle *ep;
> -
> -		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
> -						     0, next_id,
> -						     FWNODE_GRAPH_ENDPOINT_NEXT);
> -		if (!ep)
> -			break;
> +		struct fwnode_handle *source;
>  
>  		ret = v4l2_fwnode_endpoint_parse(ep, &vep);
> -		if (ret)
> -			goto err_parse;
> +		if (ret) {
> +			dev_err(rkisp1->dev, "failed to parse endpoint %pfw\n",
> +				ep);
> +			break;
> +		}
>  
>  		source = fwnode_graph_get_remote_endpoint(ep);
>  		if (!source) {
> @@ -188,14 +187,15 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>  				"endpoint %pfw has no remote endpoint\n",
>  				ep);
>  			ret = -ENODEV;
> -			goto err_parse;
> +			break;
>  		}
>  
>  		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
>  						  struct rkisp1_sensor_async);
>  		if (IS_ERR(rk_asd)) {
> +			fwnode_handle_put(source);
>  			ret = PTR_ERR(rk_asd);
> -			goto err_parse;
> +			break;
>  		}
>  
>  		rk_asd->index = index++;
> @@ -206,27 +206,23 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>  
>  		dev_dbg(rkisp1->dev, "registered ep id %d with %d lanes\n",
>  			vep.base.id, rk_asd->lanes);
> +	}
>  
> -		next_id = vep.base.id + 1;
> -
> -		fwnode_handle_put(ep);
> -
> -		continue;
> -err_parse:
> +	if (ret) {
>  		fwnode_handle_put(ep);
> -		fwnode_handle_put(source);
>  		v4l2_async_nf_cleanup(ntf);
>  		return ret;
>  	}
>  
> -	if (next_id == 0)
> +	if (!index)
>  		dev_dbg(rkisp1->dev, "no remote subdevice found\n");
> -	ntf->ops = &rkisp1_subdev_notifier_ops;
> +
>  	ret = v4l2_async_nf_register(&rkisp1->v4l2_dev, ntf);
>  	if (ret) {
>  		v4l2_async_nf_cleanup(ntf);
>  		return ret;
>  	}
> +
>  	return 0;
>  }
>  

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 42/55] media: rkisp1: Use fwnode_graph_for_each_endpoint
@ 2022-06-17 22:56     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 22:56 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:14AM +0900, Paul Elder wrote:
> When registering the notifier, replace the manual while loop with
> fwnode_graph_for_each_endpoint. This simplifies error handling.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 44 +++++++++----------
>  1 file changed, 20 insertions(+), 24 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index a3e182c86bdd..00ace8224575 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -158,29 +158,28 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
>  static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>  {
>  	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
> -	unsigned int next_id = 0;
> +	struct fwnode_handle *fwnode = dev_fwnode(rkisp1->dev);
> +	struct fwnode_handle *ep;
>  	unsigned int index = 0;
> -	int ret;
> +	int ret = 0;
>  
>  	v4l2_async_nf_init(ntf);
>  
> -	while (1) {
> +	ntf->ops = &rkisp1_subdev_notifier_ops;
> +
> +	fwnode_graph_for_each_endpoint(fwnode, ep) {
>  		struct v4l2_fwnode_endpoint vep = {
>  			.bus_type = V4L2_MBUS_CSI2_DPHY
>  		};
>  		struct rkisp1_sensor_async *rk_asd;
> -		struct fwnode_handle *source = NULL;
> -		struct fwnode_handle *ep;
> -
> -		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
> -						     0, next_id,
> -						     FWNODE_GRAPH_ENDPOINT_NEXT);
> -		if (!ep)
> -			break;
> +		struct fwnode_handle *source;
>  
>  		ret = v4l2_fwnode_endpoint_parse(ep, &vep);
> -		if (ret)
> -			goto err_parse;
> +		if (ret) {
> +			dev_err(rkisp1->dev, "failed to parse endpoint %pfw\n",
> +				ep);
> +			break;
> +		}
>  
>  		source = fwnode_graph_get_remote_endpoint(ep);
>  		if (!source) {
> @@ -188,14 +187,15 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>  				"endpoint %pfw has no remote endpoint\n",
>  				ep);
>  			ret = -ENODEV;
> -			goto err_parse;
> +			break;
>  		}
>  
>  		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
>  						  struct rkisp1_sensor_async);
>  		if (IS_ERR(rk_asd)) {
> +			fwnode_handle_put(source);
>  			ret = PTR_ERR(rk_asd);
> -			goto err_parse;
> +			break;
>  		}
>  
>  		rk_asd->index = index++;
> @@ -206,27 +206,23 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>  
>  		dev_dbg(rkisp1->dev, "registered ep id %d with %d lanes\n",
>  			vep.base.id, rk_asd->lanes);
> +	}
>  
> -		next_id = vep.base.id + 1;
> -
> -		fwnode_handle_put(ep);
> -
> -		continue;
> -err_parse:
> +	if (ret) {
>  		fwnode_handle_put(ep);
> -		fwnode_handle_put(source);
>  		v4l2_async_nf_cleanup(ntf);
>  		return ret;
>  	}
>  
> -	if (next_id == 0)
> +	if (!index)
>  		dev_dbg(rkisp1->dev, "no remote subdevice found\n");
> -	ntf->ops = &rkisp1_subdev_notifier_ops;
> +
>  	ret = v4l2_async_nf_register(&rkisp1->v4l2_dev, ntf);
>  	if (ret) {
>  		v4l2_async_nf_cleanup(ntf);
>  		return ret;
>  	}
> +
>  	return 0;
>  }
>  

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
  2022-06-16  8:05     ` Alexander Stein
@ 2022-06-17 23:03       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:03 UTC (permalink / raw)
  To: Alexander Stein
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Alexander,

On Thu, Jun 16, 2022 at 10:05:06AM +0200, Alexander Stein wrote:
> Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> > The ISP that is integrated in the i.MX8MP uses different bits in the
> > MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> > compared to the on in the RK3399. In addition, it adds a new bit for
> > enabling crop. Add new definitions for these bits for i.MX8MP devices,
> > and update where they are set.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
> >  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
> >  2 files changed, 12 insertions(+), 2 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> > 34f4fe09c88d..24ad2ccec2a3 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > @@ -168,6 +168,10 @@
> >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> > 
> > +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> > +
> 
> Does it make sense to move this kind of information into struct rkisp1_info? 
> This way you can skip the if (isp_ver == ...) thing.

Good question. Paul, what do you think ? If it doesn't get moved to the
structure, I think I'd condition it by the RKISP1_FEATURE_RSZ_CROP
feature bit instead of a version check, as it seems closely related. I'm
actually leaning towards the latter.

> >  /* RSZ_CROP_[XY]_DIR */
> >  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> > 08bf3aa8088f..29a31b18a082 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> > rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> > RKISP1_CIF_RSZ_CTRL);
> > 
> >  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> > +		else
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> >  	else
> > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> > +		else
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > 
> >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
> >  }

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
@ 2022-06-17 23:03       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:03 UTC (permalink / raw)
  To: Alexander Stein
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Alexander,

On Thu, Jun 16, 2022 at 10:05:06AM +0200, Alexander Stein wrote:
> Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> > The ISP that is integrated in the i.MX8MP uses different bits in the
> > MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> > compared to the on in the RK3399. In addition, it adds a new bit for
> > enabling crop. Add new definitions for these bits for i.MX8MP devices,
> > and update where they are set.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
> >  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
> >  2 files changed, 12 insertions(+), 2 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> > 34f4fe09c88d..24ad2ccec2a3 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > @@ -168,6 +168,10 @@
> >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> > 
> > +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> > +
> 
> Does it make sense to move this kind of information into struct rkisp1_info? 
> This way you can skip the if (isp_ver == ...) thing.

Good question. Paul, what do you think ? If it doesn't get moved to the
structure, I think I'd condition it by the RKISP1_FEATURE_RSZ_CROP
feature bit instead of a version check, as it seems closely related. I'm
actually leaning towards the latter.

> >  /* RSZ_CROP_[XY]_DIR */
> >  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> > 08bf3aa8088f..29a31b18a082 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> > rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> > RKISP1_CIF_RSZ_CTRL);
> > 
> >  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> > +		else
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> >  	else
> > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> > +		else
> > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > 
> >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
> >  }

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 23:13     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:13 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:15AM +0900, Paul Elder wrote:
> The rkisp1 can take an input on the parallel interface. Add a port for
> it, and update the required field. At least one port is required, and
> both may be specified.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
>  1 file changed, 21 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> index d1489b177331..b3661d7d4357 100644
> --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> @@ -84,8 +84,27 @@ properties:
>                  minItems: 1
>                  maxItems: 4
>  
> -    required:
> -      - port@0
> +      port@1:
> +        $ref: /schemas/graph.yaml#/$defs/port-base
> +        unevaluatedProperties: false
> +        description: connection point for input on the parallel interface
> +
> +        properties:
> +          bus-type:
> +            enum: [5, 6]
> +
> +          endpoint:
> +            $ref: video-interfaces.yaml#
> +            unevaluatedProperties: false
> +
> +        required:
> +          - bus-type
> +
> +    anyOf:
> +      - required:
> +          - port@0
> +      - required:
> +          - port@1
>  
>  required:
>    - compatible

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
@ 2022-06-17 23:13     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:13 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:15AM +0900, Paul Elder wrote:
> The rkisp1 can take an input on the parallel interface. Add a port for
> it, and update the required field. At least one port is required, and
> both may be specified.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
>  1 file changed, 21 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> index d1489b177331..b3661d7d4357 100644
> --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> @@ -84,8 +84,27 @@ properties:
>                  minItems: 1
>                  maxItems: 4
>  
> -    required:
> -      - port@0
> +      port@1:
> +        $ref: /schemas/graph.yaml#/$defs/port-base
> +        unevaluatedProperties: false
> +        description: connection point for input on the parallel interface
> +
> +        properties:
> +          bus-type:
> +            enum: [5, 6]
> +
> +          endpoint:
> +            $ref: video-interfaces.yaml#
> +            unevaluatedProperties: false
> +
> +        required:
> +          - bus-type
> +
> +    anyOf:
> +      - required:
> +          - port@0
> +      - required:
> +          - port@1
>  
>  required:
>    - compatible

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 47/55] dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 23:14     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:14 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:19AM +0900, Paul Elder wrote:
> The i.MX8MP ISP is compatbile with the rkisp1 driver. Add it to the list
> of compatible strings. While at it, expand on the description of the
> clocks to make it clear which clock in the i.MX8MP ISP they map to,
> based on the names from the datasheet (which are confusing).
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  Documentation/devicetree/bindings/media/rockchip-isp1.yaml | 7 ++++---
>  1 file changed, 4 insertions(+), 3 deletions(-)
> 
> diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> index b3661d7d4357..95cf945f7ac5 100644
> --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> @@ -16,6 +16,7 @@ description: |
>  properties:
>    compatible:
>      enum:
> +      - fsl,imx8mp-isp
>        - rockchip,px30-cif-isp
>        - rockchip,rk3399-cif-isp
>  
> @@ -36,9 +37,9 @@ properties:
>      minItems: 3
>      items:
>        # isp0 and isp1
> -      - description: ISP clock
> -      - description: ISP AXI clock
> -      - description: ISP AHB clock
> +      - description: ISP clock (for imx8mp, clk)
> +      - description: ISP AXI clock (for imx8mp, m_hclk)
> +      - description: ISP AHB clock (for imx8mp, hclk)
>        # only for isp1
>        - description: ISP Pixel clock
>  

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 47/55] dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible
@ 2022-06-17 23:14     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:14 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:19AM +0900, Paul Elder wrote:
> The i.MX8MP ISP is compatbile with the rkisp1 driver. Add it to the list
> of compatible strings. While at it, expand on the description of the
> clocks to make it clear which clock in the i.MX8MP ISP they map to,
> based on the names from the datasheet (which are confusing).
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  Documentation/devicetree/bindings/media/rockchip-isp1.yaml | 7 ++++---
>  1 file changed, 4 insertions(+), 3 deletions(-)
> 
> diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> index b3661d7d4357..95cf945f7ac5 100644
> --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> @@ -16,6 +16,7 @@ description: |
>  properties:
>    compatible:
>      enum:
> +      - fsl,imx8mp-isp
>        - rockchip,px30-cif-isp
>        - rockchip,rk3399-cif-isp
>  
> @@ -36,9 +37,9 @@ properties:
>      minItems: 3
>      items:
>        # isp0 and isp1
> -      - description: ISP clock
> -      - description: ISP AXI clock
> -      - description: ISP AHB clock
> +      - description: ISP clock (for imx8mp, clk)
> +      - description: ISP AXI clock (for imx8mp, m_hclk)
> +      - description: ISP AHB clock (for imx8mp, hclk)
>        # only for isp1
>        - description: ISP Pixel clock
>  

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-17 23:26     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:26 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
>  include/uapi/linux/rkisp1-config.h            |  3 +++
>  2 files changed, 25 insertions(+)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index 62fa2bd275fe..3a0115bdcee5 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
>  	.features = RKISP1_FEATURE_MIPI_CSI2,
>  };
>  
> +static const char * const imx8mp_isp_clks[] = {
> +	"isp",
> +	"hclk",
> +	"aclk",
> +};
> +
> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
> +	{ NULL, rkisp1_isr },
> +};
> +
> +static const struct rkisp1_info imx8mp_isp_info = {
> +	.clks = imx8mp_isp_clks,
> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
> +	.isrs = imx8mp_isp_isrs,
> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> +	.isp_ver = IMX8MP_V10,
> +};
> +
>  static const struct of_device_id rkisp1_of_match[] = {
>  	{
>  		.compatible = "rockchip,px30-cif-isp",
> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
>  		.compatible = "rockchip,rk3399-cif-isp",
>  		.data = &rk3399_isp_info,
>  	},
> +	{
> +		.compatible = "fsl,imx8mp-isp",
> +		.data = &imx8mp_isp_info,
> +	},
>  	{},
>  };
>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
> index 583ca0d9a79d..40677d47825c 100644
> --- a/include/uapi/linux/rkisp1-config.h
> +++ b/include/uapi/linux/rkisp1-config.h
> @@ -140,12 +140,15 @@
>   * @RKISP1_V11: declared in the original vendor code, but not used
>   * @RKISP1_V12: used at least in rk3326 and px30
>   * @RKISP1_V13: used at least in rk1808
> + * @IMX8MP_V10: used in at least imx8mp
>   */
>  enum rkisp1_cif_isp_version {
>  	RKISP1_V10 = 10,
>  	RKISP1_V11,
>  	RKISP1_V12,
>  	RKISP1_V13,
> +	/* TODO Choose a better version for this */
> +	IMX8MP_V10,

Time to address this ? :-)

Does anyone know where the current versioning scheme come from ?

>  };
>  
>  enum rkisp1_cif_isp_histogram_mode {

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
@ 2022-06-17 23:26     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-17 23:26 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
> 
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
>  include/uapi/linux/rkisp1-config.h            |  3 +++
>  2 files changed, 25 insertions(+)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index 62fa2bd275fe..3a0115bdcee5 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
>  	.features = RKISP1_FEATURE_MIPI_CSI2,
>  };
>  
> +static const char * const imx8mp_isp_clks[] = {
> +	"isp",
> +	"hclk",
> +	"aclk",
> +};
> +
> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
> +	{ NULL, rkisp1_isr },
> +};
> +
> +static const struct rkisp1_info imx8mp_isp_info = {
> +	.clks = imx8mp_isp_clks,
> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
> +	.isrs = imx8mp_isp_isrs,
> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> +	.isp_ver = IMX8MP_V10,
> +};
> +
>  static const struct of_device_id rkisp1_of_match[] = {
>  	{
>  		.compatible = "rockchip,px30-cif-isp",
> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
>  		.compatible = "rockchip,rk3399-cif-isp",
>  		.data = &rk3399_isp_info,
>  	},
> +	{
> +		.compatible = "fsl,imx8mp-isp",
> +		.data = &imx8mp_isp_info,
> +	},
>  	{},
>  };
>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
> index 583ca0d9a79d..40677d47825c 100644
> --- a/include/uapi/linux/rkisp1-config.h
> +++ b/include/uapi/linux/rkisp1-config.h
> @@ -140,12 +140,15 @@
>   * @RKISP1_V11: declared in the original vendor code, but not used
>   * @RKISP1_V12: used at least in rk3326 and px30
>   * @RKISP1_V13: used at least in rk1808
> + * @IMX8MP_V10: used in at least imx8mp
>   */
>  enum rkisp1_cif_isp_version {
>  	RKISP1_V10 = 10,
>  	RKISP1_V11,
>  	RKISP1_V12,
>  	RKISP1_V13,
> +	/* TODO Choose a better version for this */
> +	IMX8MP_V10,

Time to address this ? :-)

Does anyone know where the current versioning scheme come from ?

>  };
>  
>  enum rkisp1_cif_isp_histogram_mode {

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-17 22:40         ` Laurent Pinchart
@ 2022-06-18  9:35           ` Daniel Scally
  -1 siblings, 0 replies; 298+ messages in thread
From: Daniel Scally @ 2022-06-18  9:35 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, helen.koike, linux-rockchip

Morning Laurent

On 17/06/2022 23:40, Laurent Pinchart wrote:
> Hi Daniel,
>
> On Fri, Jun 17, 2022 at 11:33:03PM +0100, Daniel Scally wrote:
>> On 17/06/2022 22:34, Daniel Scally wrote:
>>> On 14/06/2022 20:11, Paul Elder wrote:
>>>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>>>
>>>> The media_entity_remote_pad() helper function returns the first remote
>>>> pad it find connected to a given pad. Beside being possibly ill-named
>>>> (as it operates on a pad, not an entity) and non-deterministic (as it
>>>> stops at the first enabled link), the fact that it returns the first
>>>> match makes it unsuitable for drivers that need to guarantee that a
>>>> single link is enabled, for instance when an entity can process data
>>>> from one of multiple sources at a time.
>>>>
>>>> For those use cases, add a new helper function,
>>>> media_entity_remote_pad_unique(), that operates on an entity and returns
>>>> a remote pad, with a guarantee that only one link is enabled. To ease
>>>> its use in drivers, also add an inline wrapper that locates source pads
>>>> specifically. A wrapper that locates sink pads can easily be added when
>>>> needed.
>>>>
>>>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>>> ---
>>>>  Documentation/driver-api/media/mc-core.rst |  4 +-
>>>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>>>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>>>>  3 files changed, 85 insertions(+), 2 deletions(-)
>>>>
>>>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
>>>> index 02481a2513b9..a2d1e32e3abb 100644
>>>> --- a/Documentation/driver-api/media/mc-core.rst
>>>> +++ b/Documentation/driver-api/media/mc-core.rst
>>>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>>>>  
>>>>  Helper functions can be used to find a link between two given pads, or a pad
>>>>  connected to another pad through an enabled link
>>>> -:c:func:`media_entity_find_link()` and
>>>> -:c:func:`media_entity_remote_pad()`.
>>>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
>>>> +:c:func:`media_entity_remote_source_pad()`).
>>>>  
>>>>  Use count and power handling
>>>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>>>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
>>>> index 11f5207f73aa..1febf5a86be6 100644
>>>> --- a/drivers/media/mc/mc-entity.c
>>>> +++ b/drivers/media/mc/mc-entity.c
>>>> @@ -9,6 +9,7 @@
>>>>   */
>>>>  
>>>>  #include <linux/bitmap.h>
>>>> +#include <linux/list.h>
>>>>  #include <linux/property.h>
>>>>  #include <linux/slab.h>
>>>>  #include <media/media-entity.h>
>>>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>>>>  }
>>>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>>>>  
>>>> +struct media_pad *
>>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>>> +			       unsigned int type)
>>>> +{
>>>> +	struct media_pad *pad = NULL;
>>>> +	struct media_link *link;
>>>> +
>>>> +	list_for_each_entry(link, &entity->links, list) {
>>>> +		struct media_pad *local_pad;
>>>> +		struct media_pad *remote_pad;
>>>> +
>>>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
>>>> +			continue;
>>> Does this need another guard here to make sure the link isn't an
>>> ancillary link? Only likely to happen at least in the immediate future
>>> where the entity represents a camera sensor, so possibly not applicable
>>> here - I couldn't find where the new function is used in the series to
>>> check. I _think_ it would actually work ok regardless...media_gobj
>>> type-punning makes my brain ache, but I think the local_pad->entity ==
>>> entity comparison would actually compare the entity->name member of the
>>> entity at the end of an ancillary link to the entity parameter, not find
>>> a match and so continue the loop without failing, but that feels a bit
>>> sub-optimal.
>> Or perhaps a better approach would be to provide something like a
>> "list_for_each_data_link()" iterator - the potential problem here (as
>> with Quentin's recent issue with the rkisp1 driver) is the assumption
>> that all links are data links, so maybe it's best to just guarantee that
>> if we can.
> I agree with you, without a dedicated iterator, we're bound to repeat
> the mistake over and over.
>
> Would you like to submit a patch to add that iterator, or should I ? I'd
> name it for_each_media_entity_data_link() or something similar.


I've started one - I'll send it later (using your function name though,
naming things was never my strong suit!)

>
>>>> +
>>>> +		if (type == MEDIA_PAD_FL_SOURCE) {
>>>> +			local_pad = link->sink;
>>>> +			remote_pad = link->source;
>>>> +		} else {
>>>> +			local_pad = link->source;
>>>> +			remote_pad = link->sink;
>>>> +		}
>>>> +
>>>> +		if (local_pad->entity == entity) {
>>>> +			if (pad)
>>>> +				return ERR_PTR(-ENOTUNIQ);
>>>> +
>>>> +			pad = remote_pad;
>>>> +		}
>>>> +	}
>>>> +
>>>> +	if (!pad)
>>>> +		return ERR_PTR(-ENOLINK);
>>>> +
>>>> +	return pad;
>>>> +}
>>>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>>>> +
>>>>  static void media_interface_init(struct media_device *mdev,
>>>>  				 struct media_interface *intf,
>>>>  				 u32 gobj_type,
>>>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
>>>> index a9a1c0ec5d1c..33d5f52719a0 100644
>>>> --- a/include/media/media-entity.h
>>>> +++ b/include/media/media-entity.h
>>>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>>>>   */
>>>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>>>>  
>>>> +/**
>>>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
>>>> + * @entity: The entity
>>>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
>>>> + *
>>>> + * Search for and return a remote pad of @type connected to @entity through an
>>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>>> + * is returned.
>>>> + *
>>>> + * The uniqueness constraint makes this helper function suitable for entities
>>>> + * that support a single active source or sink at a time.
>>>> + *
>>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>>> + * if an error occurs:
>>>> + *
>>>> + * * -ENOTUNIQ - Multiple links are enabled
>>>> + * * -ENOLINK - No connected pad found
>>>> + */
>>>> +struct media_pad *
>>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>>> +			       unsigned int type);
>>>> +
>>>> +/**
>>>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
>>>> + * @entity: The entity
>>>> + *
>>>> + * Search for and return a remote source pad connected to @entity through an
>>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>>> + * is returned.
>>>> + *
>>>> + * The uniqueness constraint makes this helper function suitable for entities
>>>> + * that support a single active source at a time.
>>>> + *
>>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>>> + * if an error occurs:
>>>> + *
>>>> + * * -ENOTUNIQ - Multiple links are enabled
>>>> + * * -ENOLINK - No connected pad found
>>>> + */
>>>> +static inline struct media_pad *
>>>> +media_entity_remote_source_pad(const struct media_entity *entity)
>>>> +{
>>>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>>>> +}
>>>> +
>>>>  /**
>>>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>>>>   * @entity: The entity

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-18  9:35           ` Daniel Scally
  0 siblings, 0 replies; 298+ messages in thread
From: Daniel Scally @ 2022-06-18  9:35 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, helen.koike, linux-rockchip

Morning Laurent

On 17/06/2022 23:40, Laurent Pinchart wrote:
> Hi Daniel,
>
> On Fri, Jun 17, 2022 at 11:33:03PM +0100, Daniel Scally wrote:
>> On 17/06/2022 22:34, Daniel Scally wrote:
>>> On 14/06/2022 20:11, Paul Elder wrote:
>>>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>>>
>>>> The media_entity_remote_pad() helper function returns the first remote
>>>> pad it find connected to a given pad. Beside being possibly ill-named
>>>> (as it operates on a pad, not an entity) and non-deterministic (as it
>>>> stops at the first enabled link), the fact that it returns the first
>>>> match makes it unsuitable for drivers that need to guarantee that a
>>>> single link is enabled, for instance when an entity can process data
>>>> from one of multiple sources at a time.
>>>>
>>>> For those use cases, add a new helper function,
>>>> media_entity_remote_pad_unique(), that operates on an entity and returns
>>>> a remote pad, with a guarantee that only one link is enabled. To ease
>>>> its use in drivers, also add an inline wrapper that locates source pads
>>>> specifically. A wrapper that locates sink pads can easily be added when
>>>> needed.
>>>>
>>>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>>> ---
>>>>  Documentation/driver-api/media/mc-core.rst |  4 +-
>>>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>>>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>>>>  3 files changed, 85 insertions(+), 2 deletions(-)
>>>>
>>>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
>>>> index 02481a2513b9..a2d1e32e3abb 100644
>>>> --- a/Documentation/driver-api/media/mc-core.rst
>>>> +++ b/Documentation/driver-api/media/mc-core.rst
>>>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>>>>  
>>>>  Helper functions can be used to find a link between two given pads, or a pad
>>>>  connected to another pad through an enabled link
>>>> -:c:func:`media_entity_find_link()` and
>>>> -:c:func:`media_entity_remote_pad()`.
>>>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
>>>> +:c:func:`media_entity_remote_source_pad()`).
>>>>  
>>>>  Use count and power handling
>>>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>>>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
>>>> index 11f5207f73aa..1febf5a86be6 100644
>>>> --- a/drivers/media/mc/mc-entity.c
>>>> +++ b/drivers/media/mc/mc-entity.c
>>>> @@ -9,6 +9,7 @@
>>>>   */
>>>>  
>>>>  #include <linux/bitmap.h>
>>>> +#include <linux/list.h>
>>>>  #include <linux/property.h>
>>>>  #include <linux/slab.h>
>>>>  #include <media/media-entity.h>
>>>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>>>>  }
>>>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>>>>  
>>>> +struct media_pad *
>>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>>> +			       unsigned int type)
>>>> +{
>>>> +	struct media_pad *pad = NULL;
>>>> +	struct media_link *link;
>>>> +
>>>> +	list_for_each_entry(link, &entity->links, list) {
>>>> +		struct media_pad *local_pad;
>>>> +		struct media_pad *remote_pad;
>>>> +
>>>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
>>>> +			continue;
>>> Does this need another guard here to make sure the link isn't an
>>> ancillary link? Only likely to happen at least in the immediate future
>>> where the entity represents a camera sensor, so possibly not applicable
>>> here - I couldn't find where the new function is used in the series to
>>> check. I _think_ it would actually work ok regardless...media_gobj
>>> type-punning makes my brain ache, but I think the local_pad->entity ==
>>> entity comparison would actually compare the entity->name member of the
>>> entity at the end of an ancillary link to the entity parameter, not find
>>> a match and so continue the loop without failing, but that feels a bit
>>> sub-optimal.
>> Or perhaps a better approach would be to provide something like a
>> "list_for_each_data_link()" iterator - the potential problem here (as
>> with Quentin's recent issue with the rkisp1 driver) is the assumption
>> that all links are data links, so maybe it's best to just guarantee that
>> if we can.
> I agree with you, without a dedicated iterator, we're bound to repeat
> the mistake over and over.
>
> Would you like to submit a patch to add that iterator, or should I ? I'd
> name it for_each_media_entity_data_link() or something similar.


I've started one - I'll send it later (using your function name though,
naming things was never my strong suit!)

>
>>>> +
>>>> +		if (type == MEDIA_PAD_FL_SOURCE) {
>>>> +			local_pad = link->sink;
>>>> +			remote_pad = link->source;
>>>> +		} else {
>>>> +			local_pad = link->source;
>>>> +			remote_pad = link->sink;
>>>> +		}
>>>> +
>>>> +		if (local_pad->entity == entity) {
>>>> +			if (pad)
>>>> +				return ERR_PTR(-ENOTUNIQ);
>>>> +
>>>> +			pad = remote_pad;
>>>> +		}
>>>> +	}
>>>> +
>>>> +	if (!pad)
>>>> +		return ERR_PTR(-ENOLINK);
>>>> +
>>>> +	return pad;
>>>> +}
>>>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>>>> +
>>>>  static void media_interface_init(struct media_device *mdev,
>>>>  				 struct media_interface *intf,
>>>>  				 u32 gobj_type,
>>>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
>>>> index a9a1c0ec5d1c..33d5f52719a0 100644
>>>> --- a/include/media/media-entity.h
>>>> +++ b/include/media/media-entity.h
>>>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>>>>   */
>>>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>>>>  
>>>> +/**
>>>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
>>>> + * @entity: The entity
>>>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
>>>> + *
>>>> + * Search for and return a remote pad of @type connected to @entity through an
>>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>>> + * is returned.
>>>> + *
>>>> + * The uniqueness constraint makes this helper function suitable for entities
>>>> + * that support a single active source or sink at a time.
>>>> + *
>>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>>> + * if an error occurs:
>>>> + *
>>>> + * * -ENOTUNIQ - Multiple links are enabled
>>>> + * * -ENOLINK - No connected pad found
>>>> + */
>>>> +struct media_pad *
>>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>>> +			       unsigned int type);
>>>> +
>>>> +/**
>>>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
>>>> + * @entity: The entity
>>>> + *
>>>> + * Search for and return a remote source pad connected to @entity through an
>>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>>> + * is returned.
>>>> + *
>>>> + * The uniqueness constraint makes this helper function suitable for entities
>>>> + * that support a single active source at a time.
>>>> + *
>>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>>> + * if an error occurs:
>>>> + *
>>>> + * * -ENOTUNIQ - Multiple links are enabled
>>>> + * * -ENOLINK - No connected pad found
>>>> + */
>>>> +static inline struct media_pad *
>>>> +media_entity_remote_source_pad(const struct media_entity *entity)
>>>> +{
>>>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>>>> +}
>>>> +
>>>>  /**
>>>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>>>>   * @entity: The entity

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-20 14:27     ` Hans Verkuil
  -1 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-20 14:27 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 6/14/22 21:10, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> Drivers typically extend the v4l2_async_subdev structure by embedding it
> in a driver-specific structure, to store per-subdev custom data. The
> v4l2_async_subdev instances are freed by the v4l2-async framework, which
> makes this mechanism cumbersome to use safely when custom data needs
> special treatment to be destroyed (such as freeing additional memory, or
> releasing references to kernel objects).
> 
> To ease this, add a .destroy() operation to the
> v4l2_async_notifier_operations structure. The operation is called right
> before the v4l2_async_subdev is freed, giving drivers a chance to
> destroy data if needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

Looks good!

Regards,

	Hans

> ---
>  Documentation/driver-api/media/v4l2-subdev.rst |  6 ++++++
>  drivers/media/v4l2-core/v4l2-async.c           | 10 ++++++++++
>  include/media/v4l2-async.h                     |  2 ++
>  3 files changed, 18 insertions(+)
> 
> diff --git a/Documentation/driver-api/media/v4l2-subdev.rst b/Documentation/driver-api/media/v4l2-subdev.rst
> index cf3b52bdbfb9..6f8d79926aa5 100644
> --- a/Documentation/driver-api/media/v4l2-subdev.rst
> +++ b/Documentation/driver-api/media/v4l2-subdev.rst
> @@ -243,6 +243,12 @@ notifier callback is called. After all subdevices have been located the
>  .complete() callback is called. When a subdevice is removed from the
>  system the .unbind() method is called. All three callbacks are optional.
>  
> +Drivers can store any type of custom data in their driver-specific
> +:c:type:`v4l2_async_subdev` wrapper. If any of that data requires special
> +handling when the structure is freed, drivers must implement the ``.destroy()``
> +notifier callback. The framework will call it right before freeing the
> +:c:type:`v4l2_async_subdev`.
> +
>  Calling subdev operations
>  ~~~~~~~~~~~~~~~~~~~~~~~~~
>  
> diff --git a/drivers/media/v4l2-core/v4l2-async.c b/drivers/media/v4l2-core/v4l2-async.c
> index c6995718237a..735dede624b8 100644
> --- a/drivers/media/v4l2-core/v4l2-async.c
> +++ b/drivers/media/v4l2-core/v4l2-async.c
> @@ -52,6 +52,15 @@ static int v4l2_async_nf_call_complete(struct v4l2_async_notifier *n)
>  	return n->ops->complete(n);
>  }
>  
> +static void v4l2_async_nf_call_destroy(struct v4l2_async_notifier *n,
> +				       struct v4l2_async_subdev *asd)
> +{
> +	if (!n->ops || !n->ops->destroy)
> +		return;
> +
> +	n->ops->destroy(asd);
> +}
> +
>  static bool match_i2c(struct v4l2_async_notifier *notifier,
>  		      struct v4l2_subdev *sd, struct v4l2_async_subdev *asd)
>  {
> @@ -626,6 +635,7 @@ static void __v4l2_async_nf_cleanup(struct v4l2_async_notifier *notifier)
>  		}
>  
>  		list_del(&asd->asd_list);
> +		v4l2_async_nf_call_destroy(notifier, asd);
>  		kfree(asd);
>  	}
>  }
> diff --git a/include/media/v4l2-async.h b/include/media/v4l2-async.h
> index 13ff3ad948f4..25eb1d138c06 100644
> --- a/include/media/v4l2-async.h
> +++ b/include/media/v4l2-async.h
> @@ -81,6 +81,7 @@ struct v4l2_async_subdev {
>   * @complete:	All subdevices have been probed successfully. The complete
>   *		callback is only executed for the root notifier.
>   * @unbind:	a subdevice is leaving
> + * @destroy:	the asd is about to be freed
>   */
>  struct v4l2_async_notifier_operations {
>  	int (*bound)(struct v4l2_async_notifier *notifier,
> @@ -90,6 +91,7 @@ struct v4l2_async_notifier_operations {
>  	void (*unbind)(struct v4l2_async_notifier *notifier,
>  		       struct v4l2_subdev *subdev,
>  		       struct v4l2_async_subdev *asd);
> +	void (*destroy)(struct v4l2_async_subdev *asd);
>  };
>  
>  /**


_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances
@ 2022-06-20 14:27     ` Hans Verkuil
  0 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-06-20 14:27 UTC (permalink / raw)
  To: Paul Elder, linux-media
  Cc: Laurent Pinchart, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 6/14/22 21:10, Paul Elder wrote:
> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> 
> Drivers typically extend the v4l2_async_subdev structure by embedding it
> in a driver-specific structure, to store per-subdev custom data. The
> v4l2_async_subdev instances are freed by the v4l2-async framework, which
> makes this mechanism cumbersome to use safely when custom data needs
> special treatment to be destroyed (such as freeing additional memory, or
> releasing references to kernel objects).
> 
> To ease this, add a .destroy() operation to the
> v4l2_async_notifier_operations structure. The operation is called right
> before the v4l2_async_subdev is freed, giving drivers a chance to
> destroy data if needed.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Hans Verkuil <hverkuil-cisco@xs4all.nl>

Looks good!

Regards,

	Hans

> ---
>  Documentation/driver-api/media/v4l2-subdev.rst |  6 ++++++
>  drivers/media/v4l2-core/v4l2-async.c           | 10 ++++++++++
>  include/media/v4l2-async.h                     |  2 ++
>  3 files changed, 18 insertions(+)
> 
> diff --git a/Documentation/driver-api/media/v4l2-subdev.rst b/Documentation/driver-api/media/v4l2-subdev.rst
> index cf3b52bdbfb9..6f8d79926aa5 100644
> --- a/Documentation/driver-api/media/v4l2-subdev.rst
> +++ b/Documentation/driver-api/media/v4l2-subdev.rst
> @@ -243,6 +243,12 @@ notifier callback is called. After all subdevices have been located the
>  .complete() callback is called. When a subdevice is removed from the
>  system the .unbind() method is called. All three callbacks are optional.
>  
> +Drivers can store any type of custom data in their driver-specific
> +:c:type:`v4l2_async_subdev` wrapper. If any of that data requires special
> +handling when the structure is freed, drivers must implement the ``.destroy()``
> +notifier callback. The framework will call it right before freeing the
> +:c:type:`v4l2_async_subdev`.
> +
>  Calling subdev operations
>  ~~~~~~~~~~~~~~~~~~~~~~~~~
>  
> diff --git a/drivers/media/v4l2-core/v4l2-async.c b/drivers/media/v4l2-core/v4l2-async.c
> index c6995718237a..735dede624b8 100644
> --- a/drivers/media/v4l2-core/v4l2-async.c
> +++ b/drivers/media/v4l2-core/v4l2-async.c
> @@ -52,6 +52,15 @@ static int v4l2_async_nf_call_complete(struct v4l2_async_notifier *n)
>  	return n->ops->complete(n);
>  }
>  
> +static void v4l2_async_nf_call_destroy(struct v4l2_async_notifier *n,
> +				       struct v4l2_async_subdev *asd)
> +{
> +	if (!n->ops || !n->ops->destroy)
> +		return;
> +
> +	n->ops->destroy(asd);
> +}
> +
>  static bool match_i2c(struct v4l2_async_notifier *notifier,
>  		      struct v4l2_subdev *sd, struct v4l2_async_subdev *asd)
>  {
> @@ -626,6 +635,7 @@ static void __v4l2_async_nf_cleanup(struct v4l2_async_notifier *notifier)
>  		}
>  
>  		list_del(&asd->asd_list);
> +		v4l2_async_nf_call_destroy(notifier, asd);
>  		kfree(asd);
>  	}
>  }
> diff --git a/include/media/v4l2-async.h b/include/media/v4l2-async.h
> index 13ff3ad948f4..25eb1d138c06 100644
> --- a/include/media/v4l2-async.h
> +++ b/include/media/v4l2-async.h
> @@ -81,6 +81,7 @@ struct v4l2_async_subdev {
>   * @complete:	All subdevices have been probed successfully. The complete
>   *		callback is only executed for the root notifier.
>   * @unbind:	a subdevice is leaving
> + * @destroy:	the asd is about to be freed
>   */
>  struct v4l2_async_notifier_operations {
>  	int (*bound)(struct v4l2_async_notifier *notifier,
> @@ -90,6 +91,7 @@ struct v4l2_async_notifier_operations {
>  	void (*unbind)(struct v4l2_async_notifier *notifier,
>  		       struct v4l2_subdev *subdev,
>  		       struct v4l2_async_subdev *asd);
> +	void (*destroy)(struct v4l2_async_subdev *asd);
>  };
>  
>  /**


^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 02/55] media: rkisp1: Enable compilation on ARCH_MXC
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:17     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:17 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP used by the Rockchip RK3399 is also found in the NXP i.MX8MP.
>Enable compilation of the driver for the MXC architecture in addition to
>ARCH_ROCKCHIP.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> drivers/media/platform/rockchip/rkisp1/Kconfig | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/Kconfig b/drivers/media/platform/rockchip/rkisp1/Kconfig
>index dabd7e42c193..731c9acbf6ef 100644
>--- a/drivers/media/platform/rockchip/rkisp1/Kconfig
>+++ b/drivers/media/platform/rockchip/rkisp1/Kconfig
>@@ -3,7 +3,7 @@ config VIDEO_ROCKCHIP_ISP1
> 	tristate "Rockchip Image Signal Processing v1 Unit driver"
> 	depends on V4L_PLATFORM_DRIVERS
> 	depends on VIDEO_DEV && OF
>-	depends on ARCH_ROCKCHIP || COMPILE_TEST
>+	depends on ARCH_ROCKCHIP || ARCH_MXC || COMPILE_TEST

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

> 	select MEDIA_CONTROLLER
> 	select VIDEO_V4L2_SUBDEV_API
> 	select VIDEOBUF2_DMA_CONTIG
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 02/55] media: rkisp1: Enable compilation on ARCH_MXC
@ 2022-06-24 14:17     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:17 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP used by the Rockchip RK3399 is also found in the NXP i.MX8MP.
>Enable compilation of the driver for the MXC architecture in addition to
>ARCH_ROCKCHIP.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> drivers/media/platform/rockchip/rkisp1/Kconfig | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/Kconfig b/drivers/media/platform/rockchip/rkisp1/Kconfig
>index dabd7e42c193..731c9acbf6ef 100644
>--- a/drivers/media/platform/rockchip/rkisp1/Kconfig
>+++ b/drivers/media/platform/rockchip/rkisp1/Kconfig
>@@ -3,7 +3,7 @@ config VIDEO_ROCKCHIP_ISP1
> 	tristate "Rockchip Image Signal Processing v1 Unit driver"
> 	depends on V4L_PLATFORM_DRIVERS
> 	depends on VIDEO_DEV && OF
>-	depends on ARCH_ROCKCHIP || COMPILE_TEST
>+	depends on ARCH_ROCKCHIP || ARCH_MXC || COMPILE_TEST

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

> 	select MEDIA_CONTROLLER
> 	select VIDEO_V4L2_SUBDEV_API
> 	select VIDEOBUF2_DMA_CONTIG
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 04/55] media: rkisp1: Disable runtime PM in probe error path
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:21     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:21 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>If the v4l2_device_register() call fails, runtime PM is left enabled.
>Fix it.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 3 ++-
> 1 file changed, 2 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 97d569968285..248f0172ca62 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -523,7 +523,7 @@ static int rkisp1_probe(struct platform_device *pdev)
>
> 	ret = v4l2_device_register(rkisp1->dev, &rkisp1->v4l2_dev);
> 	if (ret)
>-		return ret;
>+		goto err_pm_runtime_disable;
>
> 	ret = media_device_register(&rkisp1->media_dev);
> 	if (ret) {
>@@ -543,6 +543,7 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	media_device_unregister(&rkisp1->media_dev);
> err_unreg_v4l2_dev:
> 	v4l2_device_unregister(&rkisp1->v4l2_dev);
>+err_pm_runtime_disable:
> 	pm_runtime_disable(&pdev->dev);
> 	return ret;
> }
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 04/55] media: rkisp1: Disable runtime PM in probe error path
@ 2022-06-24 14:21     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:21 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>If the v4l2_device_register() call fails, runtime PM is left enabled.
>Fix it.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 3 ++-
> 1 file changed, 2 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 97d569968285..248f0172ca62 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -523,7 +523,7 @@ static int rkisp1_probe(struct platform_device *pdev)
>
> 	ret = v4l2_device_register(rkisp1->dev, &rkisp1->v4l2_dev);
> 	if (ret)
>-		return ret;
>+		goto err_pm_runtime_disable;
>
> 	ret = media_device_register(&rkisp1->media_dev);
> 	if (ret) {
>@@ -543,6 +543,7 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	media_device_unregister(&rkisp1->media_dev);
> err_unreg_v4l2_dev:
> 	v4l2_device_unregister(&rkisp1->v4l2_dev);
>+err_pm_runtime_disable:
> 	pm_runtime_disable(&pdev->dev);
> 	return ret;
> }
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 05/55] media: rkisp1: Read the ID register at probe time instead of streamon
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:26     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:26 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>There's no need to read the ID register every time streaming is started.
>Do it once, at probe time.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 10 ++++++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c |  4 ----
> 2 files changed, 10 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 248f0172ca62..ba773c0784fb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -467,6 +467,7 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	struct v4l2_device *v4l2_dev;
> 	unsigned int i;
> 	int ret, irq;
>+	u32 cif_id;
>
> 	match_data = of_device_get_match_data(&pdev->dev);
> 	if (!match_data)
>@@ -509,6 +510,15 @@ static int rkisp1_probe(struct platform_device *pdev)
>
> 	pm_runtime_enable(&pdev->dev);
>
>+	ret = pm_runtime_resume_and_get(&pdev->dev);
>+	if (ret)
>+		goto err_pm_runtime_disable;
>+
>+	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
>+	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
>+
>+	pm_runtime_put(&pdev->dev);
>+
> 	rkisp1->media_dev.hw_revision = match_data->isp_ver;
> 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
> 		sizeof(rkisp1->media_dev.model));
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 187d78075acb..02968656f3c0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -473,12 +473,8 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> /* Hardware configure Entry */
> static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
> {
>-	u32 cif_id;
> 	int ret;
>
>-	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
>-	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
>-
> 	ret = rkisp1_config_isp(rkisp1);
> 	if (ret)
> 		return ret;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 05/55] media: rkisp1: Read the ID register at probe time instead of streamon
@ 2022-06-24 14:26     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:26 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>There's no need to read the ID register every time streaming is started.
>Do it once, at probe time.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 10 ++++++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c |  4 ----
> 2 files changed, 10 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 248f0172ca62..ba773c0784fb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -467,6 +467,7 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	struct v4l2_device *v4l2_dev;
> 	unsigned int i;
> 	int ret, irq;
>+	u32 cif_id;
>
> 	match_data = of_device_get_match_data(&pdev->dev);
> 	if (!match_data)
>@@ -509,6 +510,15 @@ static int rkisp1_probe(struct platform_device *pdev)
>
> 	pm_runtime_enable(&pdev->dev);
>
>+	ret = pm_runtime_resume_and_get(&pdev->dev);
>+	if (ret)
>+		goto err_pm_runtime_disable;
>+
>+	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
>+	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
>+
>+	pm_runtime_put(&pdev->dev);
>+
> 	rkisp1->media_dev.hw_revision = match_data->isp_ver;
> 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
> 		sizeof(rkisp1->media_dev.model));
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 187d78075acb..02968656f3c0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -473,12 +473,8 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> /* Hardware configure Entry */
> static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
> {
>-	u32 cif_id;
> 	int ret;
>
>-	cif_id = rkisp1_read(rkisp1, RKISP1_CIF_VI_ID);
>-	dev_dbg(rkisp1->dev, "CIF_ID 0x%08x\n", cif_id);
>-
> 	ret = rkisp1_config_isp(rkisp1);
> 	if (ret)
> 		return ret;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 06/55] media: rkisp1: Rename rkisp1_match_data to rkisp1_info
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:29     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:29 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1_match_data structure contains device model-specific
>information. It it referenced from OF match data, but that's an
>implementation detail. Rename it to rkisp1_info to reflect its main
>purpose.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 34 +++++++++----------
> 1 file changed, 17 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index ba773c0784fb..258980ef4783 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -105,7 +105,7 @@ struct rkisp1_isr_data {
> 	irqreturn_t (*isr)(int irq, void *ctx);
> };
>
>-struct rkisp1_match_data {
>+struct rkisp1_info {
> 	const char * const *clks;
> 	unsigned int clk_size;
> 	const struct rkisp1_isr_data *isrs;
>@@ -420,7 +420,7 @@ static const struct rkisp1_isr_data px30_isp_isrs[] = {
> 	{ "mipi", rkisp1_mipi_isr },
> };
>
>-static const struct rkisp1_match_data px30_isp_match_data = {
>+static const struct rkisp1_info px30_isp_info = {
> 	.clks = px30_isp_clks,
> 	.clk_size = ARRAY_SIZE(px30_isp_clks),
> 	.isrs = px30_isp_isrs,
>@@ -438,7 +438,7 @@ static const struct rkisp1_isr_data rk3399_isp_isrs[] = {
> 	{ NULL, rkisp1_isr },
> };
>
>-static const struct rkisp1_match_data rk3399_isp_match_data = {
>+static const struct rkisp1_info rk3399_isp_info = {
> 	.clks = rk3399_isp_clks,
> 	.clk_size = ARRAY_SIZE(rk3399_isp_clks),
> 	.isrs = rk3399_isp_isrs,
>@@ -449,11 +449,11 @@ static const struct rkisp1_match_data rk3399_isp_match_data = {
> static const struct of_device_id rkisp1_of_match[] = {
> 	{
> 		.compatible = "rockchip,px30-cif-isp",
>-		.data = &px30_isp_match_data,
>+		.data = &px30_isp_info,
> 	},
> 	{
> 		.compatible = "rockchip,rk3399-cif-isp",
>-		.data = &rk3399_isp_match_data,
>+		.data = &rk3399_isp_info,
> 	},
> 	{},
> };
>@@ -461,7 +461,7 @@ MODULE_DEVICE_TABLE(of, rkisp1_of_match);
>
> static int rkisp1_probe(struct platform_device *pdev)
> {
>-	const struct rkisp1_match_data *match_data;
>+	const struct rkisp1_info *info;
> 	struct device *dev = &pdev->dev;
> 	struct rkisp1_device *rkisp1;
> 	struct v4l2_device *v4l2_dev;
>@@ -469,8 +469,8 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	int ret, irq;
> 	u32 cif_id;
>
>-	match_data = of_device_get_match_data(&pdev->dev);
>-	if (!match_data)
>+	info = of_device_get_match_data(&pdev->dev);
>+	if (!info)
> 		return -ENODEV;
>
> 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
>@@ -486,14 +486,14 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	if (IS_ERR(rkisp1->base_addr))
> 		return PTR_ERR(rkisp1->base_addr);
>
>-	for (i = 0; i < match_data->isr_size; i++) {
>-		irq = match_data->isrs[i].name
>-		    ? platform_get_irq_byname(pdev, match_data->isrs[i].name)
>+	for (i = 0; i < info->isr_size; i++) {
>+		irq = info->isrs[i].name
>+		    ? platform_get_irq_byname(pdev, info->isrs[i].name)
> 		    : platform_get_irq(pdev, i);
> 		if (irq < 0)
> 			return irq;
>
>-		ret = devm_request_irq(dev, irq, match_data->isrs[i].isr, IRQF_SHARED,
>+		ret = devm_request_irq(dev, irq, info->isrs[i].isr, IRQF_SHARED,
> 				       dev_driver_string(dev), dev);
> 		if (ret) {
> 			dev_err(dev, "request irq failed: %d\n", ret);
>@@ -501,12 +501,12 @@ static int rkisp1_probe(struct platform_device *pdev)
> 		}
> 	}
>
>-	for (i = 0; i < match_data->clk_size; i++)
>-		rkisp1->clks[i].id = match_data->clks[i];
>-	ret = devm_clk_bulk_get(dev, match_data->clk_size, rkisp1->clks);
>+	for (i = 0; i < info->clk_size; i++)
>+		rkisp1->clks[i].id = info->clks[i];
>+	ret = devm_clk_bulk_get(dev, info->clk_size, rkisp1->clks);
> 	if (ret)
> 		return ret;
>-	rkisp1->clk_size = match_data->clk_size;
>+	rkisp1->clk_size = info->clk_size;
>
> 	pm_runtime_enable(&pdev->dev);
>
>@@ -519,7 +519,7 @@ static int rkisp1_probe(struct platform_device *pdev)
>
> 	pm_runtime_put(&pdev->dev);
>
>-	rkisp1->media_dev.hw_revision = match_data->isp_ver;
>+	rkisp1->media_dev.hw_revision = info->isp_ver;
> 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
> 		sizeof(rkisp1->media_dev.model));
> 	rkisp1->media_dev.dev = &pdev->dev;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 06/55] media: rkisp1: Rename rkisp1_match_data to rkisp1_info
@ 2022-06-24 14:29     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:29 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1_match_data structure contains device model-specific
>information. It it referenced from OF match data, but that's an
>implementation detail. Rename it to rkisp1_info to reflect its main
>purpose.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 34 +++++++++----------
> 1 file changed, 17 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index ba773c0784fb..258980ef4783 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -105,7 +105,7 @@ struct rkisp1_isr_data {
> 	irqreturn_t (*isr)(int irq, void *ctx);
> };
>
>-struct rkisp1_match_data {
>+struct rkisp1_info {
> 	const char * const *clks;
> 	unsigned int clk_size;
> 	const struct rkisp1_isr_data *isrs;
>@@ -420,7 +420,7 @@ static const struct rkisp1_isr_data px30_isp_isrs[] = {
> 	{ "mipi", rkisp1_mipi_isr },
> };
>
>-static const struct rkisp1_match_data px30_isp_match_data = {
>+static const struct rkisp1_info px30_isp_info = {
> 	.clks = px30_isp_clks,
> 	.clk_size = ARRAY_SIZE(px30_isp_clks),
> 	.isrs = px30_isp_isrs,
>@@ -438,7 +438,7 @@ static const struct rkisp1_isr_data rk3399_isp_isrs[] = {
> 	{ NULL, rkisp1_isr },
> };
>
>-static const struct rkisp1_match_data rk3399_isp_match_data = {
>+static const struct rkisp1_info rk3399_isp_info = {
> 	.clks = rk3399_isp_clks,
> 	.clk_size = ARRAY_SIZE(rk3399_isp_clks),
> 	.isrs = rk3399_isp_isrs,
>@@ -449,11 +449,11 @@ static const struct rkisp1_match_data rk3399_isp_match_data = {
> static const struct of_device_id rkisp1_of_match[] = {
> 	{
> 		.compatible = "rockchip,px30-cif-isp",
>-		.data = &px30_isp_match_data,
>+		.data = &px30_isp_info,
> 	},
> 	{
> 		.compatible = "rockchip,rk3399-cif-isp",
>-		.data = &rk3399_isp_match_data,
>+		.data = &rk3399_isp_info,
> 	},
> 	{},
> };
>@@ -461,7 +461,7 @@ MODULE_DEVICE_TABLE(of, rkisp1_of_match);
>
> static int rkisp1_probe(struct platform_device *pdev)
> {
>-	const struct rkisp1_match_data *match_data;
>+	const struct rkisp1_info *info;
> 	struct device *dev = &pdev->dev;
> 	struct rkisp1_device *rkisp1;
> 	struct v4l2_device *v4l2_dev;
>@@ -469,8 +469,8 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	int ret, irq;
> 	u32 cif_id;
>
>-	match_data = of_device_get_match_data(&pdev->dev);
>-	if (!match_data)
>+	info = of_device_get_match_data(&pdev->dev);
>+	if (!info)
> 		return -ENODEV;
>
> 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
>@@ -486,14 +486,14 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	if (IS_ERR(rkisp1->base_addr))
> 		return PTR_ERR(rkisp1->base_addr);
>
>-	for (i = 0; i < match_data->isr_size; i++) {
>-		irq = match_data->isrs[i].name
>-		    ? platform_get_irq_byname(pdev, match_data->isrs[i].name)
>+	for (i = 0; i < info->isr_size; i++) {
>+		irq = info->isrs[i].name
>+		    ? platform_get_irq_byname(pdev, info->isrs[i].name)
> 		    : platform_get_irq(pdev, i);
> 		if (irq < 0)
> 			return irq;
>
>-		ret = devm_request_irq(dev, irq, match_data->isrs[i].isr, IRQF_SHARED,
>+		ret = devm_request_irq(dev, irq, info->isrs[i].isr, IRQF_SHARED,
> 				       dev_driver_string(dev), dev);
> 		if (ret) {
> 			dev_err(dev, "request irq failed: %d\n", ret);
>@@ -501,12 +501,12 @@ static int rkisp1_probe(struct platform_device *pdev)
> 		}
> 	}
>
>-	for (i = 0; i < match_data->clk_size; i++)
>-		rkisp1->clks[i].id = match_data->clks[i];
>-	ret = devm_clk_bulk_get(dev, match_data->clk_size, rkisp1->clks);
>+	for (i = 0; i < info->clk_size; i++)
>+		rkisp1->clks[i].id = info->clks[i];
>+	ret = devm_clk_bulk_get(dev, info->clk_size, rkisp1->clks);
> 	if (ret)
> 		return ret;
>-	rkisp1->clk_size = match_data->clk_size;
>+	rkisp1->clk_size = info->clk_size;
>
> 	pm_runtime_enable(&pdev->dev);
>
>@@ -519,7 +519,7 @@ static int rkisp1_probe(struct platform_device *pdev)
>
> 	pm_runtime_put(&pdev->dev);
>
>-	rkisp1->media_dev.hw_revision = match_data->isp_ver;
>+	rkisp1->media_dev.hw_revision = info->isp_ver;
> 	strscpy(rkisp1->media_dev.model, RKISP1_DRIVER_NAME,
> 		sizeof(rkisp1->media_dev.model));
> 	rkisp1->media_dev.dev = &pdev->dev;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:34     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:34 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>To make it possible to use the rkisp1_info after probe time (for
>instance to make code conditional on the ISP version), save it in the
>main rkisp1_device structure. To achieve this, also move the info
>structure into the common header, and document it.
>
>While at it, drop a NULL check in rkisp1_probe() for the match data as
>it can't happen.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
> 2 files changed, 25 insertions(+), 12 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index a67fe7b1dfa1..50d31a254b03 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
> 	RKISP1_ISP_PAD_MAX
> };
>
>+/*
>+ * struct rkisp1_info - Model-specific ISP Information
>+ *
>+ * @clks: array of ISP clock names
>+ * @clk_size: number of entries in the @clks array
>+ * @isrs: array of ISP interrupt descriptors
>+ * @isr_size: number of entires in the @isrs array
>+ * @isp_ver: ISP version
>+ *
>+ * This structure contains information about the ISP specific to a particular
>+ * ISP model, version, or integration in a particular SoC.
>+ */
>+struct rkisp1_info {
>+	const char * const *clks;
>+	unsigned int clk_size;
>+	const struct rkisp1_isr_data *isrs;
>+	unsigned int isr_size;
>+	enum rkisp1_cif_isp_version isp_ver;
>+};
>+
> /*
>  * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
>  *				of the v4l2-async API
>@@ -395,6 +415,7 @@ struct rkisp1_debug {
>  * @pipe:	   media pipeline
>  * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
>  * @debug:	   debug params to be exposed on debugfs
>+ * @info:	   version-specific ISP information
>  */
> struct rkisp1_device {
> 	void __iomem *base_addr;
>@@ -413,6 +434,7 @@ struct rkisp1_device {
> 	struct media_pipeline pipe;
> 	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
> 	struct rkisp1_debug debug;
>+	const struct rkisp1_info *info;
> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 258980ef4783..39ae35074062 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -105,14 +105,6 @@ struct rkisp1_isr_data {
> 	irqreturn_t (*isr)(int irq, void *ctx);
> };
>
>-struct rkisp1_info {
>-	const char * const *clks;
>-	unsigned int clk_size;
>-	const struct rkisp1_isr_data *isrs;
>-	unsigned int isr_size;
>-	enum rkisp1_cif_isp_version isp_ver;
>-};
>-
> /* ----------------------------------------------------------------------------
>  * Sensor DT bindings
>  */
>@@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	int ret, irq;
> 	u32 cif_id;
>
>-	info = of_device_get_match_data(&pdev->dev);
>-	if (!info)
>-		return -ENODEV;
>-
> 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
> 	if (!rkisp1)
> 		return -ENOMEM;
>
>+	info = of_device_get_match_data(dev);

Why did you omit the check 'if(!info)'?

thanks,
Dafna

>+	rkisp1->info = info;
>+
> 	dev_set_drvdata(dev, rkisp1);
> 	rkisp1->dev = dev;
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
@ 2022-06-24 14:34     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:34 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>To make it possible to use the rkisp1_info after probe time (for
>instance to make code conditional on the ISP version), save it in the
>main rkisp1_device structure. To achieve this, also move the info
>structure into the common header, and document it.
>
>While at it, drop a NULL check in rkisp1_probe() for the match data as
>it can't happen.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
> 2 files changed, 25 insertions(+), 12 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index a67fe7b1dfa1..50d31a254b03 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
> 	RKISP1_ISP_PAD_MAX
> };
>
>+/*
>+ * struct rkisp1_info - Model-specific ISP Information
>+ *
>+ * @clks: array of ISP clock names
>+ * @clk_size: number of entries in the @clks array
>+ * @isrs: array of ISP interrupt descriptors
>+ * @isr_size: number of entires in the @isrs array
>+ * @isp_ver: ISP version
>+ *
>+ * This structure contains information about the ISP specific to a particular
>+ * ISP model, version, or integration in a particular SoC.
>+ */
>+struct rkisp1_info {
>+	const char * const *clks;
>+	unsigned int clk_size;
>+	const struct rkisp1_isr_data *isrs;
>+	unsigned int isr_size;
>+	enum rkisp1_cif_isp_version isp_ver;
>+};
>+
> /*
>  * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
>  *				of the v4l2-async API
>@@ -395,6 +415,7 @@ struct rkisp1_debug {
>  * @pipe:	   media pipeline
>  * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
>  * @debug:	   debug params to be exposed on debugfs
>+ * @info:	   version-specific ISP information
>  */
> struct rkisp1_device {
> 	void __iomem *base_addr;
>@@ -413,6 +434,7 @@ struct rkisp1_device {
> 	struct media_pipeline pipe;
> 	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
> 	struct rkisp1_debug debug;
>+	const struct rkisp1_info *info;
> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 258980ef4783..39ae35074062 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -105,14 +105,6 @@ struct rkisp1_isr_data {
> 	irqreturn_t (*isr)(int irq, void *ctx);
> };
>
>-struct rkisp1_info {
>-	const char * const *clks;
>-	unsigned int clk_size;
>-	const struct rkisp1_isr_data *isrs;
>-	unsigned int isr_size;
>-	enum rkisp1_cif_isp_version isp_ver;
>-};
>-
> /* ----------------------------------------------------------------------------
>  * Sensor DT bindings
>  */
>@@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	int ret, irq;
> 	u32 cif_id;
>
>-	info = of_device_get_match_data(&pdev->dev);
>-	if (!info)
>-		return -ENODEV;
>-
> 	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
> 	if (!rkisp1)
> 		return -ENOMEM;
>
>+	info = of_device_get_match_data(dev);

Why did you omit the check 'if(!info)'?

thanks,
Dafna

>+	rkisp1->info = info;
>+
> 	dev_set_drvdata(dev, rkisp1);
> 	rkisp1->dev = dev;
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 08/55] media: rkisp1: Access ISP version from info pointer
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:35     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:35 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP version is stored in the media_device hw_revision field and
>access from there in the driver. Now that we store a pointer to the
>match data in the rkisp1_device structure, access the ISP version from
>there to make the code clearer and avoid depending on the media_device.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c    | 4 ++--
> drivers/media/platform/rockchip/rkisp1/rkisp1-params.c | 2 +-
> drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c  | 2 +-
> 3 files changed, 4 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 02968656f3c0..328e8fec14e9 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -417,7 +417,7 @@ static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
> 	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
>
> 	/* V12 could also use a newer csi2-host, but we don't want that yet */
>-	if (rkisp1->media_dev.hw_revision == RKISP1_V12)
>+	if (rkisp1->info->isp_ver == RKISP1_V12)
> 		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
>
> 	/* Configure Data Type and Virtual Channel */
>@@ -535,7 +535,7 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
> 	rkisp1_write(rkisp1, RKISP1_CIF_VI_ICCL, val);
>
> 	/* ensure sp and mp can run at the same time in V12 */
>-	if (rkisp1->media_dev.hw_revision == RKISP1_V12) {
>+	if (rkisp1->info->isp_ver == RKISP1_V12) {
> 		val = RKISP1_CIF_CLK_CTRL_MI_Y12 | RKISP1_CIF_CLK_CTRL_MI_SP |
> 		      RKISP1_CIF_CLK_CTRL_MI_RAW0 | RKISP1_CIF_CLK_CTRL_MI_RAW1 |
> 		      RKISP1_CIF_CLK_CTRL_MI_READ | RKISP1_CIF_CLK_CTRL_MI_RAWRD |
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
>index c88a9c0fa86e..9da7dc1bc690 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
>@@ -1801,7 +1801,7 @@ static void rkisp1_init_params(struct rkisp1_params *params)
> 	params->vdev_fmt.fmt.meta.buffersize =
> 		sizeof(struct rkisp1_params_cfg);
>
>-	if (params->rkisp1->media_dev.hw_revision == RKISP1_V12)
>+	if (params->rkisp1->info->isp_ver == RKISP1_V12)
> 		params->ops = &rkisp1_v12_params_ops;
> 	else
> 		params->ops = &rkisp1_v10_params_ops;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>index b7ae9166c52f..7d82356b5345 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>@@ -427,7 +427,7 @@ static void rkisp1_init_stats(struct rkisp1_stats *stats)
> 	stats->vdev_fmt.fmt.meta.buffersize =
> 		sizeof(struct rkisp1_stat_buffer);
>
>-	if (stats->rkisp1->media_dev.hw_revision == RKISP1_V12)
>+	if (stats->rkisp1->info->isp_ver == RKISP1_V12)
> 		stats->ops = &rkisp1_v12_stats_ops;
> 	else
> 		stats->ops = &rkisp1_v10_stats_ops;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 08/55] media: rkisp1: Access ISP version from info pointer
@ 2022-06-24 14:35     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:35 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP version is stored in the media_device hw_revision field and
>access from there in the driver. Now that we store a pointer to the
>match data in the rkisp1_device structure, access the ISP version from
>there to make the code clearer and avoid depending on the media_device.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c    | 4 ++--
> drivers/media/platform/rockchip/rkisp1/rkisp1-params.c | 2 +-
> drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c  | 2 +-
> 3 files changed, 4 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 02968656f3c0..328e8fec14e9 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -417,7 +417,7 @@ static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
> 	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
>
> 	/* V12 could also use a newer csi2-host, but we don't want that yet */
>-	if (rkisp1->media_dev.hw_revision == RKISP1_V12)
>+	if (rkisp1->info->isp_ver == RKISP1_V12)
> 		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
>
> 	/* Configure Data Type and Virtual Channel */
>@@ -535,7 +535,7 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
> 	rkisp1_write(rkisp1, RKISP1_CIF_VI_ICCL, val);
>
> 	/* ensure sp and mp can run at the same time in V12 */
>-	if (rkisp1->media_dev.hw_revision == RKISP1_V12) {
>+	if (rkisp1->info->isp_ver == RKISP1_V12) {
> 		val = RKISP1_CIF_CLK_CTRL_MI_Y12 | RKISP1_CIF_CLK_CTRL_MI_SP |
> 		      RKISP1_CIF_CLK_CTRL_MI_RAW0 | RKISP1_CIF_CLK_CTRL_MI_RAW1 |
> 		      RKISP1_CIF_CLK_CTRL_MI_READ | RKISP1_CIF_CLK_CTRL_MI_RAWRD |
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
>index c88a9c0fa86e..9da7dc1bc690 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-params.c
>@@ -1801,7 +1801,7 @@ static void rkisp1_init_params(struct rkisp1_params *params)
> 	params->vdev_fmt.fmt.meta.buffersize =
> 		sizeof(struct rkisp1_params_cfg);
>
>-	if (params->rkisp1->media_dev.hw_revision == RKISP1_V12)
>+	if (params->rkisp1->info->isp_ver == RKISP1_V12)
> 		params->ops = &rkisp1_v12_params_ops;
> 	else
> 		params->ops = &rkisp1_v10_params_ops;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>index b7ae9166c52f..7d82356b5345 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>@@ -427,7 +427,7 @@ static void rkisp1_init_stats(struct rkisp1_stats *stats)
> 	stats->vdev_fmt.fmt.meta.buffersize =
> 		sizeof(struct rkisp1_stat_buffer);
>
>-	if (stats->rkisp1->media_dev.hw_revision == RKISP1_V12)
>+	if (stats->rkisp1->info->isp_ver == RKISP1_V12)
> 		stats->ops = &rkisp1_v12_stats_ops;
> 	else
> 		stats->ops = &rkisp1_v10_stats_ops;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
  2022-06-24 14:34     ` Dafna Hirschfeld
@ 2022-06-24 14:47       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-24 14:47 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jun 24, 2022 at 05:34:00PM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:10, Paul Elder wrote:
> > To make it possible to use the rkisp1_info after probe time (for
> > instance to make code conditional on the ISP version), save it in the
> > main rkisp1_device structure. To achieve this, also move the info
> > structure into the common header, and document it.
> > 
> > While at it, drop a NULL check in rkisp1_probe() for the match data as
> > it can't happen.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
> >  2 files changed, 25 insertions(+), 12 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index a67fe7b1dfa1..50d31a254b03 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
> >  	RKISP1_ISP_PAD_MAX
> >  };
> > 
> > +/*
> > + * struct rkisp1_info - Model-specific ISP Information
> > + *
> > + * @clks: array of ISP clock names
> > + * @clk_size: number of entries in the @clks array
> > + * @isrs: array of ISP interrupt descriptors
> > + * @isr_size: number of entires in the @isrs array
> > + * @isp_ver: ISP version
> > + *
> > + * This structure contains information about the ISP specific to a particular
> > + * ISP model, version, or integration in a particular SoC.
> > + */
> > +struct rkisp1_info {
> > +	const char * const *clks;
> > +	unsigned int clk_size;
> > +	const struct rkisp1_isr_data *isrs;
> > +	unsigned int isr_size;
> > +	enum rkisp1_cif_isp_version isp_ver;
> > +};
> > +
> >  /*
> >   * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
> >   *				of the v4l2-async API
> > @@ -395,6 +415,7 @@ struct rkisp1_debug {
> >   * @pipe:	   media pipeline
> >   * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
> >   * @debug:	   debug params to be exposed on debugfs
> > + * @info:	   version-specific ISP information
> >   */
> >  struct rkisp1_device {
> >  	void __iomem *base_addr;
> > @@ -413,6 +434,7 @@ struct rkisp1_device {
> >  	struct media_pipeline pipe;
> >  	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
> >  	struct rkisp1_debug debug;
> > +	const struct rkisp1_info *info;
> >  };
> > 
> >  /*
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index 258980ef4783..39ae35074062 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -105,14 +105,6 @@ struct rkisp1_isr_data {
> >  	irqreturn_t (*isr)(int irq, void *ctx);
> >  };
> > 
> > -struct rkisp1_info {
> > -	const char * const *clks;
> > -	unsigned int clk_size;
> > -	const struct rkisp1_isr_data *isrs;
> > -	unsigned int isr_size;
> > -	enum rkisp1_cif_isp_version isp_ver;
> > -};
> > -
> >  /* ----------------------------------------------------------------------------
> >   * Sensor DT bindings
> >   */
> > @@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
> >  	int ret, irq;
> >  	u32 cif_id;
> > 
> > -	info = of_device_get_match_data(&pdev->dev);
> > -	if (!info)
> > -		return -ENODEV;
> > -
> >  	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
> >  	if (!rkisp1)
> >  		return -ENOMEM;
> > 
> > +	info = of_device_get_match_data(dev);
> 
> Why did you omit the check 'if(!info)'?

Because it can't happen. The probe() function is only called if the
platform device matches one of the of_device_id, so
of_device_get_match_data() can't return NULL.

> > +	rkisp1->info = info;
> > +
> >  	dev_set_drvdata(dev, rkisp1);
> >  	rkisp1->dev = dev;
> > 

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
@ 2022-06-24 14:47       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-24 14:47 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jun 24, 2022 at 05:34:00PM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:10, Paul Elder wrote:
> > To make it possible to use the rkisp1_info after probe time (for
> > instance to make code conditional on the ISP version), save it in the
> > main rkisp1_device structure. To achieve this, also move the info
> > structure into the common header, and document it.
> > 
> > While at it, drop a NULL check in rkisp1_probe() for the match data as
> > it can't happen.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
> >  2 files changed, 25 insertions(+), 12 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index a67fe7b1dfa1..50d31a254b03 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
> >  	RKISP1_ISP_PAD_MAX
> >  };
> > 
> > +/*
> > + * struct rkisp1_info - Model-specific ISP Information
> > + *
> > + * @clks: array of ISP clock names
> > + * @clk_size: number of entries in the @clks array
> > + * @isrs: array of ISP interrupt descriptors
> > + * @isr_size: number of entires in the @isrs array
> > + * @isp_ver: ISP version
> > + *
> > + * This structure contains information about the ISP specific to a particular
> > + * ISP model, version, or integration in a particular SoC.
> > + */
> > +struct rkisp1_info {
> > +	const char * const *clks;
> > +	unsigned int clk_size;
> > +	const struct rkisp1_isr_data *isrs;
> > +	unsigned int isr_size;
> > +	enum rkisp1_cif_isp_version isp_ver;
> > +};
> > +
> >  /*
> >   * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
> >   *				of the v4l2-async API
> > @@ -395,6 +415,7 @@ struct rkisp1_debug {
> >   * @pipe:	   media pipeline
> >   * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
> >   * @debug:	   debug params to be exposed on debugfs
> > + * @info:	   version-specific ISP information
> >   */
> >  struct rkisp1_device {
> >  	void __iomem *base_addr;
> > @@ -413,6 +434,7 @@ struct rkisp1_device {
> >  	struct media_pipeline pipe;
> >  	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
> >  	struct rkisp1_debug debug;
> > +	const struct rkisp1_info *info;
> >  };
> > 
> >  /*
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index 258980ef4783..39ae35074062 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -105,14 +105,6 @@ struct rkisp1_isr_data {
> >  	irqreturn_t (*isr)(int irq, void *ctx);
> >  };
> > 
> > -struct rkisp1_info {
> > -	const char * const *clks;
> > -	unsigned int clk_size;
> > -	const struct rkisp1_isr_data *isrs;
> > -	unsigned int isr_size;
> > -	enum rkisp1_cif_isp_version isp_ver;
> > -};
> > -
> >  /* ----------------------------------------------------------------------------
> >   * Sensor DT bindings
> >   */
> > @@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
> >  	int ret, irq;
> >  	u32 cif_id;
> > 
> > -	info = of_device_get_match_data(&pdev->dev);
> > -	if (!info)
> > -		return -ENODEV;
> > -
> >  	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
> >  	if (!rkisp1)
> >  		return -ENOMEM;
> > 
> > +	info = of_device_get_match_data(dev);
> 
> Why did you omit the check 'if(!info)'?

Because it can't happen. The probe() function is only called if the
platform device matches one of the of_device_id, so
of_device_get_match_data() can't return NULL.

> > +	rkisp1->info = info;
> > +
> >  	dev_set_drvdata(dev, rkisp1);
> >  	rkisp1->dev = dev;
> > 

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 14:54     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:54 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>The upcoming CSI receiver split from the ISP to a separate source file
>will need to be able to access the list of formats supported by the
>driver. Move it out of the ISP's header and into the common header, and
>add helper functions for accessing it so that the format list doesn't
>need to be stored in the header.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 +++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  28 ++-
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 168 ++----------------
> .../platform/rockchip/rkisp1/rkisp1-resizer.c |  14 +-
> .../platform/rockchip/rkisp1/rkisp1-stats.c   |   2 +-
> 5 files changed, 193 insertions(+), 167 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
>index cf889666e166..bb0ea20118e1 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
>@@ -5,10 +5,158 @@
>  * Copyright (C) 2019 Collabora, Ltd.
>  */
>
>+#include <media/mipi-csi2.h>
> #include <media/v4l2-rect.h>
>
> #include "rkisp1-common.h"
>
>+static const struct rkisp1_mbus_info rkisp1_formats[] = {
>+	{
>+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.direction	= RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_RGGB,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_BGGR,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_GBRG,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_GRBG,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_RGGB,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_BGGR,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_GBRG,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_GRBG,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_RGGB,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_BGGR,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_GBRG,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_GRBG,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	},
>+};
>+
>+unsigned int rkisp1_mbus_info_length(void)
>+{
>+	return ARRAY_SIZE(rkisp1_formats);
>+}
>+
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index)
>+{
>+	if (index >= rkisp1_mbus_info_length())
>+		return NULL;
>+
>+	return &rkisp1_formats[index];
>+}
>+
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code)
>+{
>+	unsigned int i;
>+
>+	for (i = 0; i < ARRAY_SIZE(rkisp1_formats); i++) {
>+		const struct rkisp1_mbus_info *fmt = &rkisp1_formats[i];
>+
>+		if (fmt->mbus_code == mbus_code)
>+			return fmt;
>+	}
>+
>+	return NULL;
>+}
>+
> static const struct v4l2_rect rkisp1_sd_min_crop = {
> 	.width = RKISP1_ISP_MIN_WIDTH,
> 	.height = RKISP1_ISP_MIN_HEIGHT,
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 50d31a254b03..c7d5c57607bd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -26,7 +26,7 @@
> struct dentry;
>
> /*
>- * flags on the 'direction' field in struct 'rkisp1_isp_mbus_info' that indicate
>+ * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
>  * on which pad the media bus format is supported
>  */
> #define RKISP1_ISP_SD_SRC			BIT(0)
>@@ -150,8 +150,8 @@ struct rkisp1_isp {
> 	struct v4l2_subdev sd;
> 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
> 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
>-	const struct rkisp1_isp_mbus_info *sink_fmt;
>-	const struct rkisp1_isp_mbus_info *src_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt;
>+	const struct rkisp1_mbus_info *src_fmt;
> 	struct mutex ops_lock; /* serialize the subdevice ops */
> 	bool is_dphy_errctrl_disabled;
> 	__u32 frame_sequence;
>@@ -438,8 +438,8 @@ struct rkisp1_device {
> };
>
> /*
>- * struct rkisp1_isp_mbus_info - ISP media bus info, Translates media bus code to hardware
>- *				 format values
>+ * struct rkisp1_mbus_info - ISP media bus info, Translates media bus code to hardware
>+ *			     format values
>  *
>  * @mbus_code: media bus code
>  * @pixel_enc: pixel encoding
>@@ -449,7 +449,7 @@ struct rkisp1_device {
>  * @bayer_pat: bayer pattern
>  * @direction: a bitmask of the flags indicating on which pad the format is supported on
>  */
>-struct rkisp1_isp_mbus_info {
>+struct rkisp1_mbus_info {
> 	u32 mbus_code;
> 	enum v4l2_pixel_encoding pixel_enc;
> 	u32 mipi_dt;
>@@ -481,6 +481,18 @@ static inline u32 rkisp1_read(struct rkisp1_device *rkisp1, unsigned int addr)
> int rkisp1_cap_enum_mbus_codes(struct rkisp1_capture *cap,
> 			       struct v4l2_subdev_mbus_code_enum *code);
>
>+/*
>+ * rkisp1_mbus_info_length - Return the number of supported mbus codes
>+ */
>+unsigned int rkisp1_mbus_info_length(void);
>+
>+/*
>+ * rkisp1_mbus_info_get_by_index - Retrieve the ith supported mbus info
>+ *
>+ * @index: index of the mbus info to fetch
>+ */
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index);
>+
> /*
>  * rkisp1_sd_adjust_crop_rect - adjust a rectangle to fit into another rectangle.
>  *
>@@ -500,11 +512,11 @@ void rkisp1_sd_adjust_crop(struct v4l2_rect *crop,
> 			   const struct v4l2_mbus_framefmt *bounds);
>
> /*
>- * rkisp1_isp_mbus_info - get the isp info of the media bus code
>+ * rkisp1_mbus_info_get_by_code - get the isp info of the media bus code
>  *
>  * @mbus_code: the media bus code
>  */
>-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code);
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code);
>
> /* rkisp1_params_configure - configure the params when stream starts.
>  *			     This function is called by the isp entity upon stream starts.
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 328e8fec14e9..89577119b571 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -15,7 +15,6 @@
> #include <linux/videodev2.h>
> #include <linux/vmalloc.h>
>
>-#include <media/mipi-csi2.h>
> #include <media/v4l2-event.h>
>
> #include "rkisp1-common.h"
>@@ -56,144 +55,10 @@
>  * +---------------------------------------------------------+
>  */
>
>-static const struct rkisp1_isp_mbus_info rkisp1_isp_formats[] = {
>-	{
>-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.direction	= RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_RGGB,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_BGGR,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_GBRG,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_GRBG,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_RGGB,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_BGGR,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_GBRG,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_GRBG,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_RGGB,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_BGGR,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_GBRG,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_GRBG,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	},
>-};
>-
> /* ----------------------------------------------------------------------------
>  * Helpers
>  */
>
>-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code)
>-{
>-	unsigned int i;
>-
>-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
>-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
>-
>-		if (fmt->mbus_code == mbus_code)
>-			return fmt;
>-	}
>-
>-	return NULL;
>-}
>-
> static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
>@@ -275,7 +140,7 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
> static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> {
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
>-	const struct rkisp1_isp_mbus_info *src_fmt, *sink_fmt;
>+	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct rkisp1_sensor_async *sensor;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>@@ -376,7 +241,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>
> static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> {
>-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> 	u32 val, input_sel;
>
> 	switch (sink_fmt->bus_width) {
>@@ -402,7 +267,7 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>
> static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
> {
>-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> 	unsigned int lanes = rkisp1->active_sensor->lanes;
> 	u32 mipi_ctrl;
>
>@@ -593,11 +458,12 @@ static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
> 		return 0;
> 	}
>
>-	if (code->index >= ARRAY_SIZE(rkisp1_isp_formats))
>+	if (code->index >= rkisp1_mbus_info_length())
> 		return -EINVAL;
>
>-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
>-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
>+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
>+		const struct rkisp1_mbus_info *fmt =
>+			rkisp1_mbus_info_get_by_index(i);
>
> 		if (fmt->direction & dir)
> 			pos++;
>@@ -619,7 +485,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
> 				      struct v4l2_subdev_state *sd_state,
> 				      struct v4l2_subdev_frame_size_enum *fse)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
>
> 	if (fse->pad == RKISP1_ISP_PAD_SINK_PARAMS ||
> 	    fse->pad == RKISP1_ISP_PAD_SOURCE_STATS)
>@@ -628,7 +494,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
> 	if (fse->index > 0)
> 		return -EINVAL;
>
>-	mbus_info = rkisp1_isp_mbus_info_get(fse->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(fse->code);
> 	if (!mbus_info)
> 		return -EINVAL;
>
>@@ -695,7 +561,7 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
> 				   struct v4l2_mbus_framefmt *format,
> 				   unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *src_fmt;
> 	const struct v4l2_rect *src_crop;
>
>@@ -705,10 +571,10 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
> 					   RKISP1_ISP_PAD_SOURCE_VIDEO, which);
>
> 	src_fmt->code = format->code;
>-	mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
> 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
> 		src_fmt->code = RKISP1_DEF_SRC_PAD_FMT;
>-		mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
>+		mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
> 	}
> 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
> 		isp->src_fmt = mbus_info;
>@@ -793,7 +659,7 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
> 				    struct v4l2_mbus_framefmt *format,
> 				    unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *sink_fmt;
> 	struct v4l2_rect *sink_crop;
>
>@@ -801,10 +667,10 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
> 					  which);
> 	sink_fmt->code = format->code;
>-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
> 		sink_fmt->code = RKISP1_DEF_SINK_PAD_FMT;
>-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	}
> 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
> 		isp->sink_fmt = mbus_info;
>@@ -1080,8 +946,8 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
> 	pads[RKISP1_ISP_PAD_SOURCE_VIDEO].flags = MEDIA_PAD_FL_SOURCE;
> 	pads[RKISP1_ISP_PAD_SOURCE_STATS].flags = MEDIA_PAD_FL_SOURCE;
>
>-	isp->sink_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SINK_PAD_FMT);
>-	isp->src_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SRC_PAD_FMT);
>+	isp->sink_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SINK_PAD_FMT);
>+	isp->src_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SRC_PAD_FMT);
>
> 	mutex_init(&isp->ops_lock);
> 	ret = media_entity_pads_init(&sd->entity, RKISP1_ISP_PAD_MAX, pads);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>index 1c07985c810d..f4caa8f684aa 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>@@ -433,14 +433,14 @@ static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
> 				   struct v4l2_mbus_framefmt *format,
> 				   unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *sink_mbus_info;
>+	const struct rkisp1_mbus_info *sink_mbus_info;
> 	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
>
> 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
> 					  which);
> 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
> 					 which);
>-	sink_mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>
> 	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
> 	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
>@@ -462,7 +462,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
> 				     struct v4l2_rect *r,
> 				     unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *sink_fmt;
> 	struct v4l2_rect *sink_crop;
>
>@@ -473,7 +473,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
> 					    which);
>
> 	/* Not crop for MP bayer raw data */
>-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>
> 	if (rsz->id == RKISP1_MAINPATH &&
> 	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
>@@ -500,7 +500,7 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
> 				    struct v4l2_mbus_framefmt *format,
> 				    unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
> 	struct v4l2_rect *sink_crop;
>
>@@ -516,10 +516,10 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
> 	else
> 		sink_fmt->code = format->code;
>
>-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
> 		sink_fmt->code = RKISP1_DEF_FMT;
>-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	}
> 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
> 		rsz->pixel_enc = mbus_info->pixel_enc;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>index 7d82356b5345..2795eef91bdd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>@@ -305,7 +305,7 @@ static void rkisp1_stats_get_bls_meas(struct rkisp1_stats *stats,
> 				      struct rkisp1_stat_buffer *pbuf)
> {
> 	struct rkisp1_device *rkisp1 = stats->rkisp1;
>-	const struct rkisp1_isp_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
>+	const struct rkisp1_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
> 	struct rkisp1_cif_isp_bls_meas_val *bls_val;
>
> 	bls_val = &pbuf->params.ae.bls_val;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common
@ 2022-06-24 14:54     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 14:54 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>The upcoming CSI receiver split from the ISP to a separate source file
>will need to be able to access the list of formats supported by the
>driver. Move it out of the ISP's header and into the common header, and
>add helper functions for accessing it so that the format list doesn't
>need to be stored in the header.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.c  | 148 +++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  28 ++-
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 168 ++----------------
> .../platform/rockchip/rkisp1/rkisp1-resizer.c |  14 +-
> .../platform/rockchip/rkisp1/rkisp1-stats.c   |   2 +-
> 5 files changed, 193 insertions(+), 167 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
>index cf889666e166..bb0ea20118e1 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.c
>@@ -5,10 +5,158 @@
>  * Copyright (C) 2019 Collabora, Ltd.
>  */
>
>+#include <media/mipi-csi2.h>
> #include <media/v4l2-rect.h>
>
> #include "rkisp1-common.h"
>
>+static const struct rkisp1_mbus_info rkisp1_formats[] = {
>+	{
>+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.direction	= RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_RGGB,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_BGGR,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_GBRG,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>+		.bayer_pat	= RKISP1_RAW_GRBG,
>+		.bus_width	= 10,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_RGGB,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_BGGR,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_GBRG,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>+		.bayer_pat	= RKISP1_RAW_GRBG,
>+		.bus_width	= 12,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_RGGB,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_BGGR,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_GBRG,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
>+		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>+		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>+		.bayer_pat	= RKISP1_RAW_GRBG,
>+		.bus_width	= 8,
>+		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	}, {
>+		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
>+		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>+		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>+		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
>+		.bus_width	= 16,
>+		.direction	= RKISP1_ISP_SD_SINK,
>+	},
>+};
>+
>+unsigned int rkisp1_mbus_info_length(void)
>+{
>+	return ARRAY_SIZE(rkisp1_formats);
>+}
>+
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index)
>+{
>+	if (index >= rkisp1_mbus_info_length())
>+		return NULL;
>+
>+	return &rkisp1_formats[index];
>+}
>+
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code)
>+{
>+	unsigned int i;
>+
>+	for (i = 0; i < ARRAY_SIZE(rkisp1_formats); i++) {
>+		const struct rkisp1_mbus_info *fmt = &rkisp1_formats[i];
>+
>+		if (fmt->mbus_code == mbus_code)
>+			return fmt;
>+	}
>+
>+	return NULL;
>+}
>+
> static const struct v4l2_rect rkisp1_sd_min_crop = {
> 	.width = RKISP1_ISP_MIN_WIDTH,
> 	.height = RKISP1_ISP_MIN_HEIGHT,
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 50d31a254b03..c7d5c57607bd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -26,7 +26,7 @@
> struct dentry;
>
> /*
>- * flags on the 'direction' field in struct 'rkisp1_isp_mbus_info' that indicate
>+ * flags on the 'direction' field in struct rkisp1_mbus_info' that indicate
>  * on which pad the media bus format is supported
>  */
> #define RKISP1_ISP_SD_SRC			BIT(0)
>@@ -150,8 +150,8 @@ struct rkisp1_isp {
> 	struct v4l2_subdev sd;
> 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
> 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
>-	const struct rkisp1_isp_mbus_info *sink_fmt;
>-	const struct rkisp1_isp_mbus_info *src_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt;
>+	const struct rkisp1_mbus_info *src_fmt;
> 	struct mutex ops_lock; /* serialize the subdevice ops */
> 	bool is_dphy_errctrl_disabled;
> 	__u32 frame_sequence;
>@@ -438,8 +438,8 @@ struct rkisp1_device {
> };
>
> /*
>- * struct rkisp1_isp_mbus_info - ISP media bus info, Translates media bus code to hardware
>- *				 format values
>+ * struct rkisp1_mbus_info - ISP media bus info, Translates media bus code to hardware
>+ *			     format values
>  *
>  * @mbus_code: media bus code
>  * @pixel_enc: pixel encoding
>@@ -449,7 +449,7 @@ struct rkisp1_device {
>  * @bayer_pat: bayer pattern
>  * @direction: a bitmask of the flags indicating on which pad the format is supported on
>  */
>-struct rkisp1_isp_mbus_info {
>+struct rkisp1_mbus_info {
> 	u32 mbus_code;
> 	enum v4l2_pixel_encoding pixel_enc;
> 	u32 mipi_dt;
>@@ -481,6 +481,18 @@ static inline u32 rkisp1_read(struct rkisp1_device *rkisp1, unsigned int addr)
> int rkisp1_cap_enum_mbus_codes(struct rkisp1_capture *cap,
> 			       struct v4l2_subdev_mbus_code_enum *code);
>
>+/*
>+ * rkisp1_mbus_info_length - Return the number of supported mbus codes
>+ */
>+unsigned int rkisp1_mbus_info_length(void);
>+
>+/*
>+ * rkisp1_mbus_info_get_by_index - Retrieve the ith supported mbus info
>+ *
>+ * @index: index of the mbus info to fetch
>+ */
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_index(unsigned int index);
>+
> /*
>  * rkisp1_sd_adjust_crop_rect - adjust a rectangle to fit into another rectangle.
>  *
>@@ -500,11 +512,11 @@ void rkisp1_sd_adjust_crop(struct v4l2_rect *crop,
> 			   const struct v4l2_mbus_framefmt *bounds);
>
> /*
>- * rkisp1_isp_mbus_info - get the isp info of the media bus code
>+ * rkisp1_mbus_info_get_by_code - get the isp info of the media bus code
>  *
>  * @mbus_code: the media bus code
>  */
>-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code);
>+const struct rkisp1_mbus_info *rkisp1_mbus_info_get_by_code(u32 mbus_code);
>
> /* rkisp1_params_configure - configure the params when stream starts.
>  *			     This function is called by the isp entity upon stream starts.
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 328e8fec14e9..89577119b571 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -15,7 +15,6 @@
> #include <linux/videodev2.h>
> #include <linux/vmalloc.h>
>
>-#include <media/mipi-csi2.h>
> #include <media/v4l2-event.h>
>
> #include "rkisp1-common.h"
>@@ -56,144 +55,10 @@
>  * +---------------------------------------------------------+
>  */
>
>-static const struct rkisp1_isp_mbus_info rkisp1_isp_formats[] = {
>-	{
>-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_2X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.direction	= RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SRGGB10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_RGGB,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SBGGR10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_BGGR,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGBRG10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_GBRG,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGRBG10_1X10,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW10,
>-		.bayer_pat	= RKISP1_RAW_GRBG,
>-		.bus_width	= 10,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SRGGB12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_RGGB,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SBGGR12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_BGGR,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGBRG12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_GBRG,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGRBG12_1X12,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW12,
>-		.bayer_pat	= RKISP1_RAW_GRBG,
>-		.bus_width	= 12,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SRGGB8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_RGGB,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SBGGR8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_BGGR,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGBRG8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_GBRG,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_SGRBG8_1X8,
>-		.pixel_enc	= V4L2_PIXEL_ENC_BAYER,
>-		.mipi_dt	= MIPI_CSI2_DT_RAW8,
>-		.bayer_pat	= RKISP1_RAW_GRBG,
>-		.bus_width	= 8,
>-		.direction	= RKISP1_ISP_SD_SINK | RKISP1_ISP_SD_SRC,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_YUYV8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCBYCR,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_YVYU8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_YCRYCB,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_UYVY8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CBYCRY,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	}, {
>-		.mbus_code	= MEDIA_BUS_FMT_VYUY8_1X16,
>-		.pixel_enc	= V4L2_PIXEL_ENC_YUV,
>-		.mipi_dt	= MIPI_CSI2_DT_YUV422_8B,
>-		.yuv_seq	= RKISP1_CIF_ISP_ACQ_PROP_CRYCBY,
>-		.bus_width	= 16,
>-		.direction	= RKISP1_ISP_SD_SINK,
>-	},
>-};
>-
> /* ----------------------------------------------------------------------------
>  * Helpers
>  */
>
>-const struct rkisp1_isp_mbus_info *rkisp1_isp_mbus_info_get(u32 mbus_code)
>-{
>-	unsigned int i;
>-
>-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
>-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
>-
>-		if (fmt->mbus_code == mbus_code)
>-			return fmt;
>-	}
>-
>-	return NULL;
>-}
>-
> static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
>@@ -275,7 +140,7 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
> static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> {
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
>-	const struct rkisp1_isp_mbus_info *src_fmt, *sink_fmt;
>+	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct rkisp1_sensor_async *sensor;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>@@ -376,7 +241,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>
> static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> {
>-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> 	u32 val, input_sel;
>
> 	switch (sink_fmt->bus_width) {
>@@ -402,7 +267,7 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>
> static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
> {
>-	const struct rkisp1_isp_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> 	unsigned int lanes = rkisp1->active_sensor->lanes;
> 	u32 mipi_ctrl;
>
>@@ -593,11 +458,12 @@ static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
> 		return 0;
> 	}
>
>-	if (code->index >= ARRAY_SIZE(rkisp1_isp_formats))
>+	if (code->index >= rkisp1_mbus_info_length())
> 		return -EINVAL;
>
>-	for (i = 0; i < ARRAY_SIZE(rkisp1_isp_formats); i++) {
>-		const struct rkisp1_isp_mbus_info *fmt = &rkisp1_isp_formats[i];
>+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
>+		const struct rkisp1_mbus_info *fmt =
>+			rkisp1_mbus_info_get_by_index(i);
>
> 		if (fmt->direction & dir)
> 			pos++;
>@@ -619,7 +485,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
> 				      struct v4l2_subdev_state *sd_state,
> 				      struct v4l2_subdev_frame_size_enum *fse)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
>
> 	if (fse->pad == RKISP1_ISP_PAD_SINK_PARAMS ||
> 	    fse->pad == RKISP1_ISP_PAD_SOURCE_STATS)
>@@ -628,7 +494,7 @@ static int rkisp1_isp_enum_frame_size(struct v4l2_subdev *sd,
> 	if (fse->index > 0)
> 		return -EINVAL;
>
>-	mbus_info = rkisp1_isp_mbus_info_get(fse->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(fse->code);
> 	if (!mbus_info)
> 		return -EINVAL;
>
>@@ -695,7 +561,7 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
> 				   struct v4l2_mbus_framefmt *format,
> 				   unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *src_fmt;
> 	const struct v4l2_rect *src_crop;
>
>@@ -705,10 +571,10 @@ static void rkisp1_isp_set_src_fmt(struct rkisp1_isp *isp,
> 					   RKISP1_ISP_PAD_SOURCE_VIDEO, which);
>
> 	src_fmt->code = format->code;
>-	mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
> 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
> 		src_fmt->code = RKISP1_DEF_SRC_PAD_FMT;
>-		mbus_info = rkisp1_isp_mbus_info_get(src_fmt->code);
>+		mbus_info = rkisp1_mbus_info_get_by_code(src_fmt->code);
> 	}
> 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
> 		isp->src_fmt = mbus_info;
>@@ -793,7 +659,7 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
> 				    struct v4l2_mbus_framefmt *format,
> 				    unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *sink_fmt;
> 	struct v4l2_rect *sink_crop;
>
>@@ -801,10 +667,10 @@ static void rkisp1_isp_set_sink_fmt(struct rkisp1_isp *isp,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
> 					  which);
> 	sink_fmt->code = format->code;
>-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
> 		sink_fmt->code = RKISP1_DEF_SINK_PAD_FMT;
>-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	}
> 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
> 		isp->sink_fmt = mbus_info;
>@@ -1080,8 +946,8 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
> 	pads[RKISP1_ISP_PAD_SOURCE_VIDEO].flags = MEDIA_PAD_FL_SOURCE;
> 	pads[RKISP1_ISP_PAD_SOURCE_STATS].flags = MEDIA_PAD_FL_SOURCE;
>
>-	isp->sink_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SINK_PAD_FMT);
>-	isp->src_fmt = rkisp1_isp_mbus_info_get(RKISP1_DEF_SRC_PAD_FMT);
>+	isp->sink_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SINK_PAD_FMT);
>+	isp->src_fmt = rkisp1_mbus_info_get_by_code(RKISP1_DEF_SRC_PAD_FMT);
>
> 	mutex_init(&isp->ops_lock);
> 	ret = media_entity_pads_init(&sd->entity, RKISP1_ISP_PAD_MAX, pads);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>index 1c07985c810d..f4caa8f684aa 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>@@ -433,14 +433,14 @@ static void rkisp1_rsz_set_src_fmt(struct rkisp1_resizer *rsz,
> 				   struct v4l2_mbus_framefmt *format,
> 				   unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *sink_mbus_info;
>+	const struct rkisp1_mbus_info *sink_mbus_info;
> 	struct v4l2_mbus_framefmt *src_fmt, *sink_fmt;
>
> 	sink_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SINK,
> 					  which);
> 	src_fmt = rkisp1_rsz_get_pad_fmt(rsz, sd_state, RKISP1_RSZ_PAD_SRC,
> 					 which);
>-	sink_mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	sink_mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>
> 	/* for YUV formats, userspace can change the mbus code on the src pad if it is supported */
> 	if (sink_mbus_info->pixel_enc == V4L2_PIXEL_ENC_YUV &&
>@@ -462,7 +462,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
> 				     struct v4l2_rect *r,
> 				     unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *sink_fmt;
> 	struct v4l2_rect *sink_crop;
>
>@@ -473,7 +473,7 @@ static void rkisp1_rsz_set_sink_crop(struct rkisp1_resizer *rsz,
> 					    which);
>
> 	/* Not crop for MP bayer raw data */
>-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>
> 	if (rsz->id == RKISP1_MAINPATH &&
> 	    mbus_info->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
>@@ -500,7 +500,7 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
> 				    struct v4l2_mbus_framefmt *format,
> 				    unsigned int which)
> {
>-	const struct rkisp1_isp_mbus_info *mbus_info;
>+	const struct rkisp1_mbus_info *mbus_info;
> 	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
> 	struct v4l2_rect *sink_crop;
>
>@@ -516,10 +516,10 @@ static void rkisp1_rsz_set_sink_fmt(struct rkisp1_resizer *rsz,
> 	else
> 		sink_fmt->code = format->code;
>
>-	mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SRC)) {
> 		sink_fmt->code = RKISP1_DEF_FMT;
>-		mbus_info = rkisp1_isp_mbus_info_get(sink_fmt->code);
>+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> 	}
> 	if (which == V4L2_SUBDEV_FORMAT_ACTIVE)
> 		rsz->pixel_enc = mbus_info->pixel_enc;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>index 7d82356b5345..2795eef91bdd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-stats.c
>@@ -305,7 +305,7 @@ static void rkisp1_stats_get_bls_meas(struct rkisp1_stats *stats,
> 				      struct rkisp1_stat_buffer *pbuf)
> {
> 	struct rkisp1_device *rkisp1 = stats->rkisp1;
>-	const struct rkisp1_isp_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
>+	const struct rkisp1_mbus_info *in_fmt = rkisp1->isp.sink_fmt;
> 	struct rkisp1_cif_isp_bls_meas_val *bls_val;
>
> 	bls_val = &pbuf->params.ae.bls_val;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 15:00     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 15:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>When a link validation failure occurs, print a debug message to help
>diagnosing the cause.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
> 1 file changed, 9 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>index 94819e6c23e2..94a0d787a312 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>@@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct media_link *link)
>
> 	if (sd_fmt.format.height != cap->pix.fmt.height ||
> 	    sd_fmt.format.width != cap->pix.fmt.width ||
>-	    sd_fmt.format.code != fmt->mbus)
>+	    sd_fmt.format.code != fmt->mbus) {
>+		dev_dbg(cap->rkisp1->dev,
>+			"link '%s':%u -> '%s':%u not valid: 0x%04x/%ux%u != 0x%04x/%ux%u",

missing '\n'

thanks,
Dafna

>+			link->source->entity->name, link->source->index,
>+			link->sink->entity->name, link->sink->index,
>+			sd_fmt.format.code, sd_fmt.format.width,
>+			sd_fmt.format.height, fmt->mbus, cap->pix.fmt.width,
>+			cap->pix.fmt.height);
> 		return -EPIPE;
>+	}
>
> 	return 0;
> }
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation
@ 2022-06-24 15:00     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 15:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>When a link validation failure occurs, print a debug message to help
>diagnosing the cause.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../media/platform/rockchip/rkisp1/rkisp1-capture.c    | 10 +++++++++-
> 1 file changed, 9 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>index 94819e6c23e2..94a0d787a312 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>@@ -1294,8 +1294,16 @@ static int rkisp1_capture_link_validate(struct media_link *link)
>
> 	if (sd_fmt.format.height != cap->pix.fmt.height ||
> 	    sd_fmt.format.width != cap->pix.fmt.width ||
>-	    sd_fmt.format.code != fmt->mbus)
>+	    sd_fmt.format.code != fmt->mbus) {
>+		dev_dbg(cap->rkisp1->dev,
>+			"link '%s':%u -> '%s':%u not valid: 0x%04x/%ux%u != 0x%04x/%ux%u",

missing '\n'

thanks,
Dafna

>+			link->source->entity->name, link->source->index,
>+			link->sink->entity->name, link->sink->index,
>+			sd_fmt.format.code, sd_fmt.format.width,
>+			sd_fmt.format.height, fmt->mbus, cap->pix.fmt.width,
>+			cap->pix.fmt.height);
> 		return -EPIPE;
>+	}
>
> 	return 0;
> }
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 11/55] media: rkisp1: Move sensor .s_stream() call to ISP
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 15:14     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 15:14 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Move the calls to the active sensor's .s_stream() operation to the ISP
>subdev's .s_stream(). This groups all handling of the active sensor in
>one place, preparing for a rework of that code.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-capture.c  | 12 +-----------
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c  | 11 +++++++++++
> 2 files changed, 12 insertions(+), 11 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>index 94a0d787a312..9edaa95fa44c 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>@@ -926,11 +926,8 @@ static void rkisp1_pipeline_stream_disable(struct rkisp1_capture *cap)
> 	 * If the other capture is streaming, isp and sensor nodes shouldn't
> 	 * be disabled, skip them.
> 	 */
>-	if (rkisp1->pipe.streaming_count < 2) {
>-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-				 false);
>+	if (rkisp1->pipe.streaming_count < 2)
> 		v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
>-	}
>
> 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
> 			 false);
>@@ -966,15 +963,8 @@ static int rkisp1_pipeline_stream_enable(struct rkisp1_capture *cap)
> 	if (ret)
> 		goto err_disable_rsz;
>
>-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-			       true);
>-	if (ret)
>-		goto err_disable_isp;
>-
> 	return 0;
>
>-err_disable_isp:
>-	v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
> err_disable_rsz:
> 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
> 			 false);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 89577119b571..58cf6d21f1eb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -857,6 +857,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	int ret = 0;
>
> 	if (!enable) {
>+		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>+				 false);
>+
> 		rkisp1_isp_stop(rkisp1);
> 		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
> 		return 0;
>@@ -886,6 +889,14 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	rkisp1_isp_start(rkisp1);
>
>+	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>+			       true);
>+	if (ret) {
>+		rkisp1_isp_stop(rkisp1);
>+		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
>+		goto mutex_unlock;
>+	}
>+
> mutex_unlock:
> 	mutex_unlock(&isp->ops_lock);
> 	return ret;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 11/55] media: rkisp1: Move sensor .s_stream() call to ISP
@ 2022-06-24 15:14     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 15:14 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Move the calls to the active sensor's .s_stream() operation to the ISP
>subdev's .s_stream(). This groups all handling of the active sensor in
>one place, preparing for a rework of that code.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-capture.c  | 12 +-----------
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c  | 11 +++++++++++
> 2 files changed, 12 insertions(+), 11 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>index 94a0d787a312..9edaa95fa44c 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>@@ -926,11 +926,8 @@ static void rkisp1_pipeline_stream_disable(struct rkisp1_capture *cap)
> 	 * If the other capture is streaming, isp and sensor nodes shouldn't
> 	 * be disabled, skip them.
> 	 */
>-	if (rkisp1->pipe.streaming_count < 2) {
>-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-				 false);
>+	if (rkisp1->pipe.streaming_count < 2)
> 		v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
>-	}
>
> 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
> 			 false);
>@@ -966,15 +963,8 @@ static int rkisp1_pipeline_stream_enable(struct rkisp1_capture *cap)
> 	if (ret)
> 		goto err_disable_rsz;
>
>-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-			       true);
>-	if (ret)
>-		goto err_disable_isp;
>-
> 	return 0;
>
>-err_disable_isp:
>-	v4l2_subdev_call(&rkisp1->isp.sd, video, s_stream, false);
> err_disable_rsz:
> 	v4l2_subdev_call(&rkisp1->resizer_devs[cap->id].sd, video, s_stream,
> 			 false);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 89577119b571..58cf6d21f1eb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -857,6 +857,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	int ret = 0;
>
> 	if (!enable) {
>+		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>+				 false);
>+
> 		rkisp1_isp_stop(rkisp1);
> 		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
> 		return 0;
>@@ -886,6 +889,14 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	rkisp1_isp_start(rkisp1);
>
>+	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>+			       true);
>+	if (ret) {
>+		rkisp1_isp_stop(rkisp1);
>+		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
>+		goto mutex_unlock;
>+	}
>+
> mutex_unlock:
> 	mutex_unlock(&isp->ops_lock);
> 	return ret;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 12/55] media: rkisp1: Reject sensors without pixel rate control at bound time
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 18:20     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:20 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1 driver requires the sensor to implement the pixel rate
>control. Trying to operate without it will cause an error when starting
>streaming. Catch the issue earlier, at bound time.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 6 ++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 -----
> 2 files changed, 6 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 39ae35074062..7fc617d51f44 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -190,6 +190,12 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>
> 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> 						V4L2_CID_PIXEL_RATE);
>+	if (!s_asd->pixel_rate_ctrl) {
>+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
>+			sd->name);
>+		return -EINVAL;
>+	}
>+
> 	s_asd->sd = sd;
> 	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
> 	if (IS_ERR(s_asd->dphy)) {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 58cf6d21f1eb..81138c676ac0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -823,11 +823,6 @@ static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
> 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> 	s64 pixel_clock;
>
>-	if (!sensor->pixel_rate_ctrl) {
>-		dev_warn(rkisp1->dev, "No pixel rate control in sensor subdev\n");
>-		return -EPIPE;
>-	}
>-
> 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> 	if (!pixel_clock) {
> 		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 12/55] media: rkisp1: Reject sensors without pixel rate control at bound time
@ 2022-06-24 18:20     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:20 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1 driver requires the sensor to implement the pixel rate
>control. Trying to operate without it will cause an error when starting
>streaming. Catch the issue earlier, at bound time.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 6 ++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 -----
> 2 files changed, 6 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 39ae35074062..7fc617d51f44 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -190,6 +190,12 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>
> 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> 						V4L2_CID_PIXEL_RATE);
>+	if (!s_asd->pixel_rate_ctrl) {
>+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
>+			sd->name);
>+		return -EINVAL;
>+	}
>+
> 	s_asd->sd = sd;
> 	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
> 	if (IS_ERR(s_asd->dphy)) {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 58cf6d21f1eb..81138c676ac0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -823,11 +823,6 @@ static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
> 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> 	s64 pixel_clock;
>
>-	if (!sensor->pixel_rate_ctrl) {
>-		dev_warn(rkisp1->dev, "No pixel rate control in sensor subdev\n");
>-		return -EPIPE;
>-	}
>-
> 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> 	if (!pixel_clock) {
> 		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 13/55] media: rkisp1: Create link from sensor to ISP at notifier bound time
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 18:40     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:40 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Links from sensors to the ISP can be created as sensors are bound. Move
>the link creation from rkisp1_create_links() to the bound notifier, and
>clean up the rkisp1_create_links() function while at it.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 87 ++++++++-----------
> 2 files changed, 40 insertions(+), 49 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index c7d5c57607bd..ba11baf75fa9 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -116,6 +116,7 @@ struct rkisp1_info {
>  *				of the v4l2-async API
>  *
>  * @asd:		async_subdev variable for the sensor
>+ * @index:		index of the sensor (counting sensor found in DT)
>  * @lanes:		number of lanes
>  * @mbus_type:		type of bus (currently only CSI2 is supported)
>  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
>@@ -125,6 +126,7 @@ struct rkisp1_info {
>  */
> struct rkisp1_sensor_async {
> 	struct v4l2_async_subdev asd;
>+	unsigned int index;
> 	unsigned int lanes;
> 	enum v4l2_mbus_type mbus_type;
> 	unsigned int mbus_flags;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 7fc617d51f44..4501aea265cb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -111,72 +111,46 @@ struct rkisp1_isr_data {
>
> static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> {
>-	struct media_entity *source, *sink;
>-	unsigned int flags, source_pad;
>-	struct v4l2_subdev *sd;
> 	unsigned int i;
> 	int ret;
>
>-	/* sensor links */
>-	flags = MEDIA_LNK_FL_ENABLED;
>-	list_for_each_entry(sd, &rkisp1->v4l2_dev.subdevs, list) {
>-		if (sd == &rkisp1->isp.sd ||
>-		    sd == &rkisp1->resizer_devs[RKISP1_MAINPATH].sd ||
>-		    sd == &rkisp1->resizer_devs[RKISP1_SELFPATH].sd)
>-			continue;
>-
>-		ret = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
>-						  MEDIA_PAD_FL_SOURCE);
>-		if (ret < 0) {
>-			dev_err(rkisp1->dev, "failed to find src pad for %s\n",
>-				sd->name);
>-			return ret;
>-		}
>-		source_pad = ret;
>-
>-		ret = media_create_pad_link(&sd->entity, source_pad,
>-					    &rkisp1->isp.sd.entity,
>-					    RKISP1_ISP_PAD_SINK_VIDEO,
>-					    flags);
>-		if (ret)
>-			return ret;
>-
>-		flags = 0;
>-	}
>-
>-	flags = MEDIA_LNK_FL_ENABLED | MEDIA_LNK_FL_IMMUTABLE;
>-
> 	/* create ISP->RSZ->CAP links */
> 	for (i = 0; i < 2; i++) {
>-		source = &rkisp1->isp.sd.entity;
>-		sink = &rkisp1->resizer_devs[i].sd.entity;
>-		ret = media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_VIDEO,
>-					    sink, RKISP1_RSZ_PAD_SINK,
>+		struct media_entity *resizer =
>+			&rkisp1->resizer_devs[i].sd.entity;
>+		struct media_entity *capture =
>+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
>+
>+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
>+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
>+					    resizer, RKISP1_RSZ_PAD_SINK,
> 					    MEDIA_LNK_FL_ENABLED);
> 		if (ret)
> 			return ret;
>
>-		source = sink;
>-		sink = &rkisp1->capture_devs[i].vnode.vdev.entity;
>-		ret = media_create_pad_link(source, RKISP1_RSZ_PAD_SRC,
>-					    sink, 0, flags);
>+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
>+					    capture, 0,
>+					    MEDIA_LNK_FL_ENABLED |
>+					    MEDIA_LNK_FL_IMMUTABLE);
> 		if (ret)
> 			return ret;
> 	}
>
> 	/* params links */
>-	source = &rkisp1->params.vnode.vdev.entity;
>-	sink = &rkisp1->isp.sd.entity;
>-	ret = media_create_pad_link(source, 0, sink,
>-				    RKISP1_ISP_PAD_SINK_PARAMS, flags);
>+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
>+				    &rkisp1->isp.sd.entity,
>+				    RKISP1_ISP_PAD_SINK_PARAMS,
>+				    MEDIA_LNK_FL_ENABLED |
>+				    MEDIA_LNK_FL_IMMUTABLE);
> 	if (ret)
> 		return ret;
>
> 	/* 3A stats links */
>-	source = &rkisp1->isp.sd.entity;
>-	sink = &rkisp1->stats.vnode.vdev.entity;
>-	return media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_STATS,
>-				     sink, 0, flags);
>+	return media_create_pad_link(&rkisp1->isp.sd.entity,
>+				     RKISP1_ISP_PAD_SOURCE_STATS,
>+				     &rkisp1->stats.vnode.vdev.entity, 0,
>+				     MEDIA_LNK_FL_ENABLED |
>+				     MEDIA_LNK_FL_IMMUTABLE);
> }
>
> static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>@@ -187,6 +161,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 		container_of(notifier, struct rkisp1_device, notifier);
> 	struct rkisp1_sensor_async *s_asd =
> 		container_of(asd, struct rkisp1_sensor_async, asd);
>+	int source_pad;
>
> 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> 						V4L2_CID_PIXEL_RATE);
>@@ -206,7 +181,19 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>
> 	phy_init(s_asd->dphy);
>
>-	return 0;
>+	/* Create the link to the sensor. */
>+	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
>+						 MEDIA_PAD_FL_SOURCE);
>+	if (source_pad < 0) {
>+		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
>+			sd->name);
>+		return source_pad;
>+	}
>+
>+	return media_create_pad_link(&sd->entity, source_pad,
>+				     &rkisp1->isp.sd.entity,
>+				     RKISP1_ISP_PAD_SINK_VIDEO,
>+				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> }
>
> static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
>@@ -248,6 +235,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
> {
> 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
> 	unsigned int next_id = 0;
>+	unsigned int index = 0;
> 	int ret;
>
> 	v4l2_async_nf_init(ntf);
>@@ -277,6 +265,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
> 			goto err_parse;
> 		}
>
>+		rk_asd->index = index++;
> 		rk_asd->mbus_type = vep.bus_type;
> 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
> 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 13/55] media: rkisp1: Create link from sensor to ISP at notifier bound time
@ 2022-06-24 18:40     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:40 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Links from sensors to the ISP can be created as sensors are bound. Move
>the link creation from rkisp1_create_links() to the bound notifier, and
>clean up the rkisp1_create_links() function while at it.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 87 ++++++++-----------
> 2 files changed, 40 insertions(+), 49 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index c7d5c57607bd..ba11baf75fa9 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -116,6 +116,7 @@ struct rkisp1_info {
>  *				of the v4l2-async API
>  *
>  * @asd:		async_subdev variable for the sensor
>+ * @index:		index of the sensor (counting sensor found in DT)
>  * @lanes:		number of lanes
>  * @mbus_type:		type of bus (currently only CSI2 is supported)
>  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
>@@ -125,6 +126,7 @@ struct rkisp1_info {
>  */
> struct rkisp1_sensor_async {
> 	struct v4l2_async_subdev asd;
>+	unsigned int index;
> 	unsigned int lanes;
> 	enum v4l2_mbus_type mbus_type;
> 	unsigned int mbus_flags;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 7fc617d51f44..4501aea265cb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -111,72 +111,46 @@ struct rkisp1_isr_data {
>
> static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> {
>-	struct media_entity *source, *sink;
>-	unsigned int flags, source_pad;
>-	struct v4l2_subdev *sd;
> 	unsigned int i;
> 	int ret;
>
>-	/* sensor links */
>-	flags = MEDIA_LNK_FL_ENABLED;
>-	list_for_each_entry(sd, &rkisp1->v4l2_dev.subdevs, list) {
>-		if (sd == &rkisp1->isp.sd ||
>-		    sd == &rkisp1->resizer_devs[RKISP1_MAINPATH].sd ||
>-		    sd == &rkisp1->resizer_devs[RKISP1_SELFPATH].sd)
>-			continue;
>-
>-		ret = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
>-						  MEDIA_PAD_FL_SOURCE);
>-		if (ret < 0) {
>-			dev_err(rkisp1->dev, "failed to find src pad for %s\n",
>-				sd->name);
>-			return ret;
>-		}
>-		source_pad = ret;
>-
>-		ret = media_create_pad_link(&sd->entity, source_pad,
>-					    &rkisp1->isp.sd.entity,
>-					    RKISP1_ISP_PAD_SINK_VIDEO,
>-					    flags);
>-		if (ret)
>-			return ret;
>-
>-		flags = 0;
>-	}
>-
>-	flags = MEDIA_LNK_FL_ENABLED | MEDIA_LNK_FL_IMMUTABLE;
>-
> 	/* create ISP->RSZ->CAP links */
> 	for (i = 0; i < 2; i++) {
>-		source = &rkisp1->isp.sd.entity;
>-		sink = &rkisp1->resizer_devs[i].sd.entity;
>-		ret = media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_VIDEO,
>-					    sink, RKISP1_RSZ_PAD_SINK,
>+		struct media_entity *resizer =
>+			&rkisp1->resizer_devs[i].sd.entity;
>+		struct media_entity *capture =
>+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
>+
>+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
>+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
>+					    resizer, RKISP1_RSZ_PAD_SINK,
> 					    MEDIA_LNK_FL_ENABLED);
> 		if (ret)
> 			return ret;
>
>-		source = sink;
>-		sink = &rkisp1->capture_devs[i].vnode.vdev.entity;
>-		ret = media_create_pad_link(source, RKISP1_RSZ_PAD_SRC,
>-					    sink, 0, flags);
>+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
>+					    capture, 0,
>+					    MEDIA_LNK_FL_ENABLED |
>+					    MEDIA_LNK_FL_IMMUTABLE);
> 		if (ret)
> 			return ret;
> 	}
>
> 	/* params links */
>-	source = &rkisp1->params.vnode.vdev.entity;
>-	sink = &rkisp1->isp.sd.entity;
>-	ret = media_create_pad_link(source, 0, sink,
>-				    RKISP1_ISP_PAD_SINK_PARAMS, flags);
>+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
>+				    &rkisp1->isp.sd.entity,
>+				    RKISP1_ISP_PAD_SINK_PARAMS,
>+				    MEDIA_LNK_FL_ENABLED |
>+				    MEDIA_LNK_FL_IMMUTABLE);
> 	if (ret)
> 		return ret;
>
> 	/* 3A stats links */
>-	source = &rkisp1->isp.sd.entity;
>-	sink = &rkisp1->stats.vnode.vdev.entity;
>-	return media_create_pad_link(source, RKISP1_ISP_PAD_SOURCE_STATS,
>-				     sink, 0, flags);
>+	return media_create_pad_link(&rkisp1->isp.sd.entity,
>+				     RKISP1_ISP_PAD_SOURCE_STATS,
>+				     &rkisp1->stats.vnode.vdev.entity, 0,
>+				     MEDIA_LNK_FL_ENABLED |
>+				     MEDIA_LNK_FL_IMMUTABLE);
> }
>
> static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>@@ -187,6 +161,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 		container_of(notifier, struct rkisp1_device, notifier);
> 	struct rkisp1_sensor_async *s_asd =
> 		container_of(asd, struct rkisp1_sensor_async, asd);
>+	int source_pad;
>
> 	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> 						V4L2_CID_PIXEL_RATE);
>@@ -206,7 +181,19 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
>
> 	phy_init(s_asd->dphy);
>
>-	return 0;
>+	/* Create the link to the sensor. */
>+	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
>+						 MEDIA_PAD_FL_SOURCE);
>+	if (source_pad < 0) {
>+		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
>+			sd->name);
>+		return source_pad;
>+	}
>+
>+	return media_create_pad_link(&sd->entity, source_pad,
>+				     &rkisp1->isp.sd.entity,
>+				     RKISP1_ISP_PAD_SINK_VIDEO,
>+				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> }
>
> static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
>@@ -248,6 +235,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
> {
> 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
> 	unsigned int next_id = 0;
>+	unsigned int index = 0;
> 	int ret;
>
> 	v4l2_async_nf_init(ntf);
>@@ -277,6 +265,7 @@ static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
> 			goto err_parse;
> 		}
>
>+		rk_asd->index = index++;
> 		rk_asd->mbus_type = vep.bus_type;
> 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
> 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 14/55] media: rkisp1: Create internal links at probe time
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 18:43     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:43 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>There's no need to wait until all async subdevs are bound before
>creating internal links. Create them at probe time.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 105 ++++++++----------
> 1 file changed, 49 insertions(+), 56 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 4501aea265cb..7bb1235cddea 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -109,50 +109,6 @@ struct rkisp1_isr_data {
>  * Sensor DT bindings
>  */
>
>-static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>-{
>-	unsigned int i;
>-	int ret;
>-
>-	/* create ISP->RSZ->CAP links */
>-	for (i = 0; i < 2; i++) {
>-		struct media_entity *resizer =
>-			&rkisp1->resizer_devs[i].sd.entity;
>-		struct media_entity *capture =
>-			&rkisp1->capture_devs[i].vnode.vdev.entity;;
>-
>-		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
>-					    RKISP1_ISP_PAD_SOURCE_VIDEO,
>-					    resizer, RKISP1_RSZ_PAD_SINK,
>-					    MEDIA_LNK_FL_ENABLED);
>-		if (ret)
>-			return ret;
>-
>-		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
>-					    capture, 0,
>-					    MEDIA_LNK_FL_ENABLED |
>-					    MEDIA_LNK_FL_IMMUTABLE);
>-		if (ret)
>-			return ret;
>-	}
>-
>-	/* params links */
>-	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
>-				    &rkisp1->isp.sd.entity,
>-				    RKISP1_ISP_PAD_SINK_PARAMS,
>-				    MEDIA_LNK_FL_ENABLED |
>-				    MEDIA_LNK_FL_IMMUTABLE);
>-	if (ret)
>-		return ret;
>-
>-	/* 3A stats links */
>-	return media_create_pad_link(&rkisp1->isp.sd.entity,
>-				     RKISP1_ISP_PAD_SOURCE_STATS,
>-				     &rkisp1->stats.vnode.vdev.entity, 0,
>-				     MEDIA_LNK_FL_ENABLED |
>-				     MEDIA_LNK_FL_IMMUTABLE);
>-}
>-
> static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 					struct v4l2_subdev *sd,
> 					struct v4l2_async_subdev *asd)
>@@ -210,19 +166,8 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> {
> 	struct rkisp1_device *rkisp1 =
> 		container_of(notifier, struct rkisp1_device, notifier);
>-	int ret;
>-
>-	ret = rkisp1_create_links(rkisp1);
>-	if (ret)
>-		return ret;
>-
>-	ret = v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
>-	if (ret)
>-		return ret;
>-
>-	dev_dbg(rkisp1->dev, "Async subdev notifier completed\n");
>
>-	return 0;
>+	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
> }
>
> static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
>@@ -332,6 +277,50 @@ static const struct dev_pm_ops rkisp1_pm_ops = {
>  * Core
>  */
>
>+static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>+{
>+	unsigned int i;
>+	int ret;
>+
>+	/* create ISP->RSZ->CAP links */
>+	for (i = 0; i < 2; i++) {
>+		struct media_entity *resizer =
>+			&rkisp1->resizer_devs[i].sd.entity;
>+		struct media_entity *capture =
>+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
>+
>+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
>+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
>+					    resizer, RKISP1_RSZ_PAD_SINK,
>+					    MEDIA_LNK_FL_ENABLED);
>+		if (ret)
>+			return ret;
>+
>+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
>+					    capture, 0,
>+					    MEDIA_LNK_FL_ENABLED |
>+					    MEDIA_LNK_FL_IMMUTABLE);
>+		if (ret)
>+			return ret;
>+	}
>+
>+	/* params links */
>+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
>+				    &rkisp1->isp.sd.entity,
>+				    RKISP1_ISP_PAD_SINK_PARAMS,
>+				    MEDIA_LNK_FL_ENABLED |
>+				    MEDIA_LNK_FL_IMMUTABLE);
>+	if (ret)
>+		return ret;
>+
>+	/* 3A stats links */
>+	return media_create_pad_link(&rkisp1->isp.sd.entity,
>+				     RKISP1_ISP_PAD_SOURCE_STATS,
>+				     &rkisp1->stats.vnode.vdev.entity, 0,
>+				     MEDIA_LNK_FL_ENABLED |
>+				     MEDIA_LNK_FL_IMMUTABLE);
>+}
>+
> static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
> {
> 	rkisp1_params_unregister(rkisp1);
>@@ -365,6 +354,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>+	ret = rkisp1_create_links(rkisp1);
>+	if (ret)
>+		goto error;
>+
> 	ret = rkisp1_subdev_notifier(rkisp1);
> 	if (ret) {
> 		dev_err(rkisp1->dev,
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 14/55] media: rkisp1: Create internal links at probe time
@ 2022-06-24 18:43     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:43 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>There's no need to wait until all async subdevs are bound before
>creating internal links. Create them at probe time.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 105 ++++++++----------
> 1 file changed, 49 insertions(+), 56 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 4501aea265cb..7bb1235cddea 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -109,50 +109,6 @@ struct rkisp1_isr_data {
>  * Sensor DT bindings
>  */
>
>-static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>-{
>-	unsigned int i;
>-	int ret;
>-
>-	/* create ISP->RSZ->CAP links */
>-	for (i = 0; i < 2; i++) {
>-		struct media_entity *resizer =
>-			&rkisp1->resizer_devs[i].sd.entity;
>-		struct media_entity *capture =
>-			&rkisp1->capture_devs[i].vnode.vdev.entity;;
>-
>-		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
>-					    RKISP1_ISP_PAD_SOURCE_VIDEO,
>-					    resizer, RKISP1_RSZ_PAD_SINK,
>-					    MEDIA_LNK_FL_ENABLED);
>-		if (ret)
>-			return ret;
>-
>-		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
>-					    capture, 0,
>-					    MEDIA_LNK_FL_ENABLED |
>-					    MEDIA_LNK_FL_IMMUTABLE);
>-		if (ret)
>-			return ret;
>-	}
>-
>-	/* params links */
>-	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
>-				    &rkisp1->isp.sd.entity,
>-				    RKISP1_ISP_PAD_SINK_PARAMS,
>-				    MEDIA_LNK_FL_ENABLED |
>-				    MEDIA_LNK_FL_IMMUTABLE);
>-	if (ret)
>-		return ret;
>-
>-	/* 3A stats links */
>-	return media_create_pad_link(&rkisp1->isp.sd.entity,
>-				     RKISP1_ISP_PAD_SOURCE_STATS,
>-				     &rkisp1->stats.vnode.vdev.entity, 0,
>-				     MEDIA_LNK_FL_ENABLED |
>-				     MEDIA_LNK_FL_IMMUTABLE);
>-}
>-
> static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 					struct v4l2_subdev *sd,
> 					struct v4l2_async_subdev *asd)
>@@ -210,19 +166,8 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> {
> 	struct rkisp1_device *rkisp1 =
> 		container_of(notifier, struct rkisp1_device, notifier);
>-	int ret;
>-
>-	ret = rkisp1_create_links(rkisp1);
>-	if (ret)
>-		return ret;
>-
>-	ret = v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
>-	if (ret)
>-		return ret;
>-
>-	dev_dbg(rkisp1->dev, "Async subdev notifier completed\n");
>
>-	return 0;
>+	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
> }
>
> static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
>@@ -332,6 +277,50 @@ static const struct dev_pm_ops rkisp1_pm_ops = {
>  * Core
>  */
>
>+static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>+{
>+	unsigned int i;
>+	int ret;
>+
>+	/* create ISP->RSZ->CAP links */
>+	for (i = 0; i < 2; i++) {
>+		struct media_entity *resizer =
>+			&rkisp1->resizer_devs[i].sd.entity;
>+		struct media_entity *capture =
>+			&rkisp1->capture_devs[i].vnode.vdev.entity;;
>+
>+		ret = media_create_pad_link(&rkisp1->isp.sd.entity,
>+					    RKISP1_ISP_PAD_SOURCE_VIDEO,
>+					    resizer, RKISP1_RSZ_PAD_SINK,
>+					    MEDIA_LNK_FL_ENABLED);
>+		if (ret)
>+			return ret;
>+
>+		ret = media_create_pad_link(resizer, RKISP1_RSZ_PAD_SRC,
>+					    capture, 0,
>+					    MEDIA_LNK_FL_ENABLED |
>+					    MEDIA_LNK_FL_IMMUTABLE);
>+		if (ret)
>+			return ret;
>+	}
>+
>+	/* params links */
>+	ret = media_create_pad_link(&rkisp1->params.vnode.vdev.entity, 0,
>+				    &rkisp1->isp.sd.entity,
>+				    RKISP1_ISP_PAD_SINK_PARAMS,
>+				    MEDIA_LNK_FL_ENABLED |
>+				    MEDIA_LNK_FL_IMMUTABLE);
>+	if (ret)
>+		return ret;
>+
>+	/* 3A stats links */
>+	return media_create_pad_link(&rkisp1->isp.sd.entity,
>+				     RKISP1_ISP_PAD_SOURCE_STATS,
>+				     &rkisp1->stats.vnode.vdev.entity, 0,
>+				     MEDIA_LNK_FL_ENABLED |
>+				     MEDIA_LNK_FL_IMMUTABLE);
>+}
>+
> static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
> {
> 	rkisp1_params_unregister(rkisp1);
>@@ -365,6 +354,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>+	ret = rkisp1_create_links(rkisp1);
>+	if (ret)
>+		goto error;
>+
> 	ret = rkisp1_subdev_notifier(rkisp1);
> 	if (ret) {
> 		dev_err(rkisp1->dev,
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 15/55] media: rkisp1: Rename rkisp1_subdev_notifier() to rkisp1_subdev_notifier_register()
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-24 18:44     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:44 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The function name isn't very clear, rename it to
>rkisp1_subdev_notifier_register().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 7bb1235cddea..386c1c17aec2 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -176,7 +176,7 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
> 	.complete = rkisp1_subdev_notifier_complete,
> };
>
>-static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
>+static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> {
> 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
> 	unsigned int next_id = 0;
>@@ -358,7 +358,7 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>-	ret = rkisp1_subdev_notifier(rkisp1);
>+	ret = rkisp1_subdev_notifier_register(rkisp1);
> 	if (ret) {
> 		dev_err(rkisp1->dev,
> 			"Failed to register subdev notifier(%d)\n", ret);
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 15/55] media: rkisp1: Rename rkisp1_subdev_notifier() to rkisp1_subdev_notifier_register()
@ 2022-06-24 18:44     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-24 18:44 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The function name isn't very clear, rename it to
>rkisp1_subdev_notifier_register().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 7bb1235cddea..386c1c17aec2 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -176,7 +176,7 @@ static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops =
> 	.complete = rkisp1_subdev_notifier_complete,
> };
>
>-static int rkisp1_subdev_notifier(struct rkisp1_device *rkisp1)
>+static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> {
> 	struct v4l2_async_notifier *ntf = &rkisp1->notifier;
> 	unsigned int next_id = 0;
>@@ -358,7 +358,7 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>-	ret = rkisp1_subdev_notifier(rkisp1);
>+	ret = rkisp1_subdev_notifier_register(rkisp1);
> 	if (ret) {
> 		dev_err(rkisp1->dev,
> 			"Failed to register subdev notifier(%d)\n", ret);
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 18/55] media: rkisp1: Split CSI handling to separate file
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  3:48     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  3:48 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>Not all ISP instances include a MIPI CSI-2 receiver. To prepare for
>making it optional, move code related to the CSI-2 receiver to a
>separate file.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../media/platform/rockchip/rkisp1/Makefile   |   1 +
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 +-
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 193 ++++++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +++
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |  32 +--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 153 +-------------
> 6 files changed, 257 insertions(+), 167 deletions(-)
> create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/Makefile b/drivers/media/platform/rockchip/rkisp1/Makefile
>index f7543a82aa10..b3844c4f7623 100644
>--- a/drivers/media/platform/rockchip/rkisp1/Makefile
>+++ b/drivers/media/platform/rockchip/rkisp1/Makefile
>@@ -2,6 +2,7 @@
>
> rockchip-isp1-y := rkisp1-capture.o \
> 		   rkisp1-common.o \
>+		   rkisp1-csi.o \
> 		   rkisp1-dev.o \
> 		   rkisp1-isp.o \
> 		   rkisp1-resizer.o \
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 60c5462e1746..a52fa9e0dd66 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -123,7 +123,6 @@ struct rkisp1_info {
>  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
>  * @sd:			a pointer to v4l2_subdev struct of the sensor
>  * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
>- * @dphy:		a pointer to the phy
>  */
> struct rkisp1_sensor_async {
> 	struct v4l2_async_subdev asd;
>@@ -134,7 +133,19 @@ struct rkisp1_sensor_async {
> 	unsigned int mbus_flags;
> 	struct v4l2_subdev *sd;
> 	struct v4l2_ctrl *pixel_rate_ctrl;
>+};
>+
>+/*
>+ * struct rkisp1_csi - CSI receiver subdev
>+ *
>+ * @rkisp1: pointer to the rkisp1 device
>+ * @dphy: a pointer to the phy
>+ * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
>+ */
>+struct rkisp1_csi {
>+	struct rkisp1_device *rkisp1;

I think you missed initializing csi->rkips1

> 	struct phy *dphy;
>+	bool is_dphy_errctrl_disabled;
> };
>
> /*
>@@ -147,7 +158,6 @@ struct rkisp1_sensor_async {
>  * @sink_fmt:			input format
>  * @src_fmt:			output format
>  * @ops_lock:			ops serialization
>- * @is_dphy_errctrl_disabled:	if dphy errctrl is disabled (avoid endless interrupt)
>  * @frame_sequence:		used to synchronize frame_id between video devices.
>  */
> struct rkisp1_isp {
>@@ -157,7 +167,6 @@ struct rkisp1_isp {
> 	const struct rkisp1_mbus_info *sink_fmt;
> 	const struct rkisp1_mbus_info *src_fmt;
> 	struct mutex ops_lock; /* serialize the subdevice ops */
>-	bool is_dphy_errctrl_disabled;
> 	__u32 frame_sequence;
> };
>
>@@ -411,6 +420,7 @@ struct rkisp1_debug {
>  * @media_dev:	   media_device variable
>  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
>  * @active_sensor: sensor in-use, set when streaming on
>+ * @csi:	   internal CSI-2 receiver
>  * @isp:	   ISP sub-device
>  * @resizer_devs:  resizer sub-devices
>  * @capture_devs:  capture devices
>@@ -430,6 +440,7 @@ struct rkisp1_device {
> 	struct media_device media_dev;
> 	struct v4l2_async_notifier notifier;
> 	struct rkisp1_sensor_async *active_sensor;
>+	struct rkisp1_csi csi;
> 	struct rkisp1_isp isp;
> 	struct rkisp1_resizer resizer_devs[2];
> 	struct rkisp1_capture capture_devs[2];
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>new file mode 100644
>index 000000000000..4af04296b625
>--- /dev/null
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -0,0 +1,193 @@
>+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
>+/*
>+ * Rockchip ISP1 Driver - CSI-2 Receiver
>+ *
>+ * Copyright (C) 2019 Collabora, Ltd.
>+ * Copyright (C) 2022 Ideas on Board
>+ *
>+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
>+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
>+ */
>+
>+#include <linux/device.h>
>+#include <linux/phy/phy.h>
>+#include <linux/phy/phy-mipi-dphy.h>
>+
>+#include <media/v4l2-ctrls.h>
>+
>+#include "rkisp1-common.h"
>+#include "rkisp1-csi.h"
>+
>+int rkisp1_config_mipi(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	unsigned int lanes = rkisp1->active_sensor->lanes;
>+	u32 mipi_ctrl;
>+
>+	if (lanes < 1 || lanes > 4)
>+		return -EINVAL;
>+
>+	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
>+		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
>+		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
>+		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
>+
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
>+
>+	/* V12 could also use a newer csi2-host, but we don't want that yet */
>+	if (rkisp1->info->isp_ver == RKISP1_V12)
>+		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
>+
>+	/* Configure Data Type and Virtual Channel */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
>+		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
>+		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
>+
>+	/* Clear MIPI interrupts */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);

new line here

>+	/*
>+	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
>+	 * isp bus may be dead when switch isp.
>+	 */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>+		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
>+		     RKISP1_CIF_MIPI_ERR_DPHY |
>+		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
>+		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
>+
>+	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
>+		"  MIPI_IMG_DATA_SEL 0x%08x\n"
>+		"  MIPI_STATUS 0x%08x\n"
>+		"  MIPI_IMSC 0x%08x\n",
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
>+
>+	return 0;
>+}
>+
>+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>+			   struct rkisp1_sensor_async *sensor)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	union phy_configure_opts opts;
>+	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
>+	s64 pixel_clock;
>+
>+	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
>+	if (!pixel_clock) {
>+		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
>+		return -EINVAL;
>+	}
>+
>+	phy_mipi_dphy_get_default_config(pixel_clock,
>+					 rkisp1->isp.sink_fmt->bus_width,
>+					 sensor->lanes, cfg);
>+	phy_set_mode(csi->dphy, PHY_MODE_MIPI_DPHY);
>+	phy_configure(csi->dphy, &opts);
>+	phy_power_on(csi->dphy);
>+
>+	return 0;
>+}
>+
>+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
>+{
>+	phy_power_off(csi->dphy);
>+}
>+
>+void rkisp1_mipi_start(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>+}
>+
>+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	/* Mask and clear interrupts. */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+}
>+
>+irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>+{
>+	struct device *dev = ctx;
>+	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
>+	u32 val, status;
>+
>+	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
>+	if (!status)
>+		return IRQ_NONE;
>+
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
>+
>+	/*
>+	 * Disable DPHY errctrl interrupt, because this dphy
>+	 * erctrl signal is asserted until the next changes
>+	 * of line state. This time is may be too long and cpu
>+	 * is hold in this interrupt.
>+	 */
>+	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
>+		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>+			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
>+		rkisp1->csi.is_dphy_errctrl_disabled = true;
>+	}
>+
>+	/*
>+	 * Enable DPHY errctrl interrupt again, if mipi have receive
>+	 * the whole frame without any error.
>+	 */
>+	if (status == RKISP1_CIF_MIPI_FRAME_END) {
>+		/*
>+		 * Enable DPHY errctrl interrupt again, if mipi have receive
>+		 * the whole frame without any error.
>+		 */
>+		if (rkisp1->csi.is_dphy_errctrl_disabled) {
>+			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>+			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
>+			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
>+			rkisp1->csi.is_dphy_errctrl_disabled = false;
>+		}
>+	} else {
>+		rkisp1->debug.mipi_error++;
>+	}
>+
>+	return IRQ_HANDLED;
>+}
>+
>+int rkisp1_csi_init(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+
>+	csi->dphy = devm_phy_get(rkisp1->dev, "dphy");
>+	if (IS_ERR(csi->dphy)) {
>+		if (PTR_ERR(csi->dphy) != -EPROBE_DEFER)
>+		dev_err_probe(rkisp1->dev, PTR_ERR(csi->dphy),
>+			      "Couldn't get the MIPI D-PHY\n");

indentation

>+		return PTR_ERR(csi->dphy);
>+	}
>+
>+	phy_init(csi->dphy);
>+
>+	return 0;
>+}
>+
>+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+
>+	phy_exit(csi->dphy);
>+}
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>new file mode 100644
>index 000000000000..d97a4ee5c002
>--- /dev/null
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -0,0 +1,28 @@
>+/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
>+/*
>+ * Rockchip ISP1 Driver - CSI-2 Receiver
>+ *
>+ * Copyright (C) 2019 Collabora, Ltd.
>+ * Copyright (C) 2022 Ideas on Board
>+ *
>+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
>+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
>+ */
>+#ifndef _RKISP1_CSI_H
>+#define _RKISP1_CSI_H
>+
>+struct rkisp1_device;
>+struct rkisp1_sensor_async;
>+
>+int rkisp1_csi_init(struct rkisp1_device *rkisp1);
>+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>+
>+int rkisp1_config_mipi(struct rkisp1_csi *csi);
>+
>+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>+			   struct rkisp1_sensor_async *sensor);
>+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
>+void rkisp1_mipi_start(struct rkisp1_csi *csi);
>+void rkisp1_mipi_stop(struct rkisp1_csi *csi);

some of the functions name here are *_csi_* and some are *_csi2_*
maybe choose consistent name?

thanks,
Dafna

>+
>+#endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 0f3e45cdbf2a..373a1f00c10a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -15,11 +15,11 @@
> #include <linux/of_graph.h>
> #include <linux/of_platform.h>
> #include <linux/pinctrl/consumer.h>
>-#include <linux/phy/phy.h>
>-#include <linux/phy/phy-mipi-dphy.h>
>+#include <linux/pm_runtime.h>
> #include <media/v4l2-fwnode.h>
>
> #include "rkisp1-common.h"
>+#include "rkisp1-csi.h"
>
> /*
>  * ISP Details
>@@ -128,14 +128,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 	}
>
> 	s_asd->sd = sd;
>-	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
>-	if (IS_ERR(s_asd->dphy)) {
>-		if (PTR_ERR(s_asd->dphy) != -EPROBE_DEFER)
>-			dev_err(rkisp1->dev, "Couldn't get the MIPI D-PHY\n");
>-		return PTR_ERR(s_asd->dphy);
>-	}
>-
>-	phy_init(s_asd->dphy);
>
> 	/* Create the link to the sensor. */
> 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
>@@ -152,16 +144,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> }
>
>-static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
>-					  struct v4l2_subdev *sd,
>-					  struct v4l2_async_subdev *asd)
>-{
>-	struct rkisp1_sensor_async *s_asd =
>-		container_of(asd, struct rkisp1_sensor_async, asd);
>-
>-	phy_exit(s_asd->dphy);
>-}
>-
> static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> {
> 	struct rkisp1_device *rkisp1 =
>@@ -180,7 +162,6 @@ static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
>
> static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> 	.bound = rkisp1_subdev_notifier_bound,
>-	.unbind = rkisp1_subdev_notifier_unbind,
> 	.complete = rkisp1_subdev_notifier_complete,
> 	.destroy = rkisp1_subdev_notifier_destroy,
> };
>@@ -540,14 +521,20 @@ static int rkisp1_probe(struct platform_device *pdev)
> 		goto err_unreg_v4l2_dev;
> 	}
>
>-	ret = rkisp1_entities_register(rkisp1);
>+	ret = rkisp1_csi_init(rkisp1);
> 	if (ret)
> 		goto err_unreg_media_dev;
>
>+	ret = rkisp1_entities_register(rkisp1);
>+	if (ret)
>+		goto err_cleanup_csi;
>+
> 	rkisp1_debug_init(rkisp1);
>
> 	return 0;
>
>+err_cleanup_csi:
>+	rkisp1_csi_cleanup(rkisp1);
> err_unreg_media_dev:
> 	media_device_unregister(&rkisp1->media_dev);
> err_unreg_v4l2_dev:
>@@ -565,6 +552,7 @@ static int rkisp1_remove(struct platform_device *pdev)
> 	v4l2_async_nf_cleanup(&rkisp1->notifier);
>
> 	rkisp1_entities_unregister(rkisp1);
>+	rkisp1_csi_cleanup(rkisp1);
> 	rkisp1_debug_cleanup(rkisp1);
>
> 	media_device_unregister(&rkisp1->media_dev);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 81138c676ac0..5eabb321e320 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -9,8 +9,6 @@
>  */
>
> #include <linux/iopoll.h>
>-#include <linux/phy/phy.h>
>-#include <linux/phy/phy-mipi-dphy.h>
> #include <linux/pm_runtime.h>
> #include <linux/videodev2.h>
> #include <linux/vmalloc.h>
>@@ -18,6 +16,7 @@
> #include <media/v4l2-event.h>
>
> #include "rkisp1-common.h"
>+#include "rkisp1-csi.h"
>
> #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
>@@ -265,55 +264,6 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> 	return 0;
> }
>
>-static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
>-{
>-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>-	unsigned int lanes = rkisp1->active_sensor->lanes;
>-	u32 mipi_ctrl;
>-
>-	if (lanes < 1 || lanes > 4)
>-		return -EINVAL;
>-
>-	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
>-		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
>-		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
>-		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
>-
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
>-
>-	/* V12 could also use a newer csi2-host, but we don't want that yet */
>-	if (rkisp1->info->isp_ver == RKISP1_V12)
>-		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
>-
>-	/* Configure Data Type and Virtual Channel */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
>-		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
>-		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
>-
>-	/* Clear MIPI interrupts */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>-	/*
>-	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
>-	 * isp bus may be dead when switch isp.
>-	 */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>-		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
>-		     RKISP1_CIF_MIPI_ERR_DPHY |
>-		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
>-		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
>-
>-	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
>-		"  MIPI_IMG_DATA_SEL 0x%08x\n"
>-		"  MIPI_STATUS 0x%08x\n"
>-		"  MIPI_IMSC 0x%08x\n",
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
>-
>-	return 0;
>-}
>-
> /* Configure MUX */
> static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> {
>@@ -326,7 +276,7 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> 		ret = rkisp1_config_dvp(rkisp1);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>-		ret = rkisp1_config_mipi(rkisp1);
>+		ret = rkisp1_config_mipi(&rkisp1->csi);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}
>
>@@ -360,17 +310,14 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> 	 * Stop ISP(isp) ->wait for ISP isp off
> 	 */
> 	/* stop and clear MI, MIPI, and ISP interrupts */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>-
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+
>+	rkisp1_mipi_stop(&rkisp1->csi);
>+
> 	/* stop ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
>@@ -417,11 +364,9 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> 	rkisp1_config_clk(rkisp1);
>
> 	/* Activate MIPI */
>-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-			     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>-	}
>+	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
>+		rkisp1_mipi_start(&rkisp1->csi);
>+
> 	/* Activate ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
>@@ -814,35 +759,6 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
>  * Stream operations
>  */
>
>-static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
>-				  struct rkisp1_sensor_async *sensor)
>-{
>-	struct rkisp1_device *rkisp1 =
>-		container_of(isp->sd.v4l2_dev, struct rkisp1_device, v4l2_dev);
>-	union phy_configure_opts opts;
>-	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
>-	s64 pixel_clock;
>-
>-	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
>-	if (!pixel_clock) {
>-		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
>-		return -EINVAL;
>-	}
>-
>-	phy_mipi_dphy_get_default_config(pixel_clock, isp->sink_fmt->bus_width,
>-					 sensor->lanes, cfg);
>-	phy_set_mode(sensor->dphy, PHY_MODE_MIPI_DPHY);
>-	phy_configure(sensor->dphy, &opts);
>-	phy_power_on(sensor->dphy);
>-
>-	return 0;
>-}
>-
>-static void rkisp1_mipi_csi2_stop(struct rkisp1_sensor_async *sensor)
>-{
>-	phy_power_off(sensor->dphy);
>-}
>-
> static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_device *rkisp1 =
>@@ -856,7 +772,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 				 false);
>
> 		rkisp1_isp_stop(rkisp1);
>-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
>+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> 		return 0;
> 	}
>
>@@ -878,7 +794,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	if (ret)
> 		goto mutex_unlock;
>
>-	ret = rkisp1_mipi_csi2_start(&rkisp1->isp, rkisp1->active_sensor);
>+	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
> 	if (ret)
> 		goto mutex_unlock;
>
>@@ -888,7 +804,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 			       true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
>-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
>+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>
>@@ -993,53 +909,6 @@ void rkisp1_isp_unregister(struct rkisp1_device *rkisp1)
>  * Interrupt handlers
>  */
>
>-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>-{
>-	struct device *dev = ctx;
>-	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
>-	u32 val, status;
>-
>-	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
>-	if (!status)
>-		return IRQ_NONE;
>-
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
>-
>-	/*
>-	 * Disable DPHY errctrl interrupt, because this dphy
>-	 * erctrl signal is asserted until the next changes
>-	 * of line state. This time is may be too long and cpu
>-	 * is hold in this interrupt.
>-	 */
>-	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
>-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>-			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
>-		rkisp1->isp.is_dphy_errctrl_disabled = true;
>-	}
>-
>-	/*
>-	 * Enable DPHY errctrl interrupt again, if mipi have receive
>-	 * the whole frame without any error.
>-	 */
>-	if (status == RKISP1_CIF_MIPI_FRAME_END) {
>-		/*
>-		 * Enable DPHY errctrl interrupt again, if mipi have receive
>-		 * the whole frame without any error.
>-		 */
>-		if (rkisp1->isp.is_dphy_errctrl_disabled) {
>-			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>-			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
>-			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
>-			rkisp1->isp.is_dphy_errctrl_disabled = false;
>-		}
>-	} else {
>-		rkisp1->debug.mipi_error++;
>-	}
>-
>-	return IRQ_HANDLED;
>-}
>-
> static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
> {
> 	struct v4l2_event event = {
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 18/55] media: rkisp1: Split CSI handling to separate file
@ 2022-06-25  3:48     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  3:48 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>Not all ISP instances include a MIPI CSI-2 receiver. To prepare for
>making it optional, move code related to the CSI-2 receiver to a
>separate file.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../media/platform/rockchip/rkisp1/Makefile   |   1 +
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 +-
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 193 ++++++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +++
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |  32 +--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 153 +-------------
> 6 files changed, 257 insertions(+), 167 deletions(-)
> create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/Makefile b/drivers/media/platform/rockchip/rkisp1/Makefile
>index f7543a82aa10..b3844c4f7623 100644
>--- a/drivers/media/platform/rockchip/rkisp1/Makefile
>+++ b/drivers/media/platform/rockchip/rkisp1/Makefile
>@@ -2,6 +2,7 @@
>
> rockchip-isp1-y := rkisp1-capture.o \
> 		   rkisp1-common.o \
>+		   rkisp1-csi.o \
> 		   rkisp1-dev.o \
> 		   rkisp1-isp.o \
> 		   rkisp1-resizer.o \
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 60c5462e1746..a52fa9e0dd66 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -123,7 +123,6 @@ struct rkisp1_info {
>  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
>  * @sd:			a pointer to v4l2_subdev struct of the sensor
>  * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
>- * @dphy:		a pointer to the phy
>  */
> struct rkisp1_sensor_async {
> 	struct v4l2_async_subdev asd;
>@@ -134,7 +133,19 @@ struct rkisp1_sensor_async {
> 	unsigned int mbus_flags;
> 	struct v4l2_subdev *sd;
> 	struct v4l2_ctrl *pixel_rate_ctrl;
>+};
>+
>+/*
>+ * struct rkisp1_csi - CSI receiver subdev
>+ *
>+ * @rkisp1: pointer to the rkisp1 device
>+ * @dphy: a pointer to the phy
>+ * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
>+ */
>+struct rkisp1_csi {
>+	struct rkisp1_device *rkisp1;

I think you missed initializing csi->rkips1

> 	struct phy *dphy;
>+	bool is_dphy_errctrl_disabled;
> };
>
> /*
>@@ -147,7 +158,6 @@ struct rkisp1_sensor_async {
>  * @sink_fmt:			input format
>  * @src_fmt:			output format
>  * @ops_lock:			ops serialization
>- * @is_dphy_errctrl_disabled:	if dphy errctrl is disabled (avoid endless interrupt)
>  * @frame_sequence:		used to synchronize frame_id between video devices.
>  */
> struct rkisp1_isp {
>@@ -157,7 +167,6 @@ struct rkisp1_isp {
> 	const struct rkisp1_mbus_info *sink_fmt;
> 	const struct rkisp1_mbus_info *src_fmt;
> 	struct mutex ops_lock; /* serialize the subdevice ops */
>-	bool is_dphy_errctrl_disabled;
> 	__u32 frame_sequence;
> };
>
>@@ -411,6 +420,7 @@ struct rkisp1_debug {
>  * @media_dev:	   media_device variable
>  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
>  * @active_sensor: sensor in-use, set when streaming on
>+ * @csi:	   internal CSI-2 receiver
>  * @isp:	   ISP sub-device
>  * @resizer_devs:  resizer sub-devices
>  * @capture_devs:  capture devices
>@@ -430,6 +440,7 @@ struct rkisp1_device {
> 	struct media_device media_dev;
> 	struct v4l2_async_notifier notifier;
> 	struct rkisp1_sensor_async *active_sensor;
>+	struct rkisp1_csi csi;
> 	struct rkisp1_isp isp;
> 	struct rkisp1_resizer resizer_devs[2];
> 	struct rkisp1_capture capture_devs[2];
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>new file mode 100644
>index 000000000000..4af04296b625
>--- /dev/null
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -0,0 +1,193 @@
>+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
>+/*
>+ * Rockchip ISP1 Driver - CSI-2 Receiver
>+ *
>+ * Copyright (C) 2019 Collabora, Ltd.
>+ * Copyright (C) 2022 Ideas on Board
>+ *
>+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
>+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
>+ */
>+
>+#include <linux/device.h>
>+#include <linux/phy/phy.h>
>+#include <linux/phy/phy-mipi-dphy.h>
>+
>+#include <media/v4l2-ctrls.h>
>+
>+#include "rkisp1-common.h"
>+#include "rkisp1-csi.h"
>+
>+int rkisp1_config_mipi(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	unsigned int lanes = rkisp1->active_sensor->lanes;
>+	u32 mipi_ctrl;
>+
>+	if (lanes < 1 || lanes > 4)
>+		return -EINVAL;
>+
>+	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
>+		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
>+		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
>+		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
>+
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
>+
>+	/* V12 could also use a newer csi2-host, but we don't want that yet */
>+	if (rkisp1->info->isp_ver == RKISP1_V12)
>+		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
>+
>+	/* Configure Data Type and Virtual Channel */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
>+		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
>+		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
>+
>+	/* Clear MIPI interrupts */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);

new line here

>+	/*
>+	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
>+	 * isp bus may be dead when switch isp.
>+	 */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>+		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
>+		     RKISP1_CIF_MIPI_ERR_DPHY |
>+		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
>+		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
>+
>+	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
>+		"  MIPI_IMG_DATA_SEL 0x%08x\n"
>+		"  MIPI_STATUS 0x%08x\n"
>+		"  MIPI_IMSC 0x%08x\n",
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
>+		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
>+
>+	return 0;
>+}
>+
>+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>+			   struct rkisp1_sensor_async *sensor)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	union phy_configure_opts opts;
>+	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
>+	s64 pixel_clock;
>+
>+	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
>+	if (!pixel_clock) {
>+		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
>+		return -EINVAL;
>+	}
>+
>+	phy_mipi_dphy_get_default_config(pixel_clock,
>+					 rkisp1->isp.sink_fmt->bus_width,
>+					 sensor->lanes, cfg);
>+	phy_set_mode(csi->dphy, PHY_MODE_MIPI_DPHY);
>+	phy_configure(csi->dphy, &opts);
>+	phy_power_on(csi->dphy);
>+
>+	return 0;
>+}
>+
>+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
>+{
>+	phy_power_off(csi->dphy);
>+}
>+
>+void rkisp1_mipi_start(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>+}
>+
>+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	/* Mask and clear interrupts. */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+}
>+
>+irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>+{
>+	struct device *dev = ctx;
>+	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
>+	u32 val, status;
>+
>+	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
>+	if (!status)
>+		return IRQ_NONE;
>+
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
>+
>+	/*
>+	 * Disable DPHY errctrl interrupt, because this dphy
>+	 * erctrl signal is asserted until the next changes
>+	 * of line state. This time is may be too long and cpu
>+	 * is hold in this interrupt.
>+	 */
>+	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
>+		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>+			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
>+		rkisp1->csi.is_dphy_errctrl_disabled = true;
>+	}
>+
>+	/*
>+	 * Enable DPHY errctrl interrupt again, if mipi have receive
>+	 * the whole frame without any error.
>+	 */
>+	if (status == RKISP1_CIF_MIPI_FRAME_END) {
>+		/*
>+		 * Enable DPHY errctrl interrupt again, if mipi have receive
>+		 * the whole frame without any error.
>+		 */
>+		if (rkisp1->csi.is_dphy_errctrl_disabled) {
>+			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>+			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
>+			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
>+			rkisp1->csi.is_dphy_errctrl_disabled = false;
>+		}
>+	} else {
>+		rkisp1->debug.mipi_error++;
>+	}
>+
>+	return IRQ_HANDLED;
>+}
>+
>+int rkisp1_csi_init(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+
>+	csi->dphy = devm_phy_get(rkisp1->dev, "dphy");
>+	if (IS_ERR(csi->dphy)) {
>+		if (PTR_ERR(csi->dphy) != -EPROBE_DEFER)
>+		dev_err_probe(rkisp1->dev, PTR_ERR(csi->dphy),
>+			      "Couldn't get the MIPI D-PHY\n");

indentation

>+		return PTR_ERR(csi->dphy);
>+	}
>+
>+	phy_init(csi->dphy);
>+
>+	return 0;
>+}
>+
>+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+
>+	phy_exit(csi->dphy);
>+}
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>new file mode 100644
>index 000000000000..d97a4ee5c002
>--- /dev/null
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -0,0 +1,28 @@
>+/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
>+/*
>+ * Rockchip ISP1 Driver - CSI-2 Receiver
>+ *
>+ * Copyright (C) 2019 Collabora, Ltd.
>+ * Copyright (C) 2022 Ideas on Board
>+ *
>+ * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
>+ * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
>+ */
>+#ifndef _RKISP1_CSI_H
>+#define _RKISP1_CSI_H
>+
>+struct rkisp1_device;
>+struct rkisp1_sensor_async;
>+
>+int rkisp1_csi_init(struct rkisp1_device *rkisp1);
>+void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>+
>+int rkisp1_config_mipi(struct rkisp1_csi *csi);
>+
>+int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>+			   struct rkisp1_sensor_async *sensor);
>+void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
>+void rkisp1_mipi_start(struct rkisp1_csi *csi);
>+void rkisp1_mipi_stop(struct rkisp1_csi *csi);

some of the functions name here are *_csi_* and some are *_csi2_*
maybe choose consistent name?

thanks,
Dafna

>+
>+#endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 0f3e45cdbf2a..373a1f00c10a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -15,11 +15,11 @@
> #include <linux/of_graph.h>
> #include <linux/of_platform.h>
> #include <linux/pinctrl/consumer.h>
>-#include <linux/phy/phy.h>
>-#include <linux/phy/phy-mipi-dphy.h>
>+#include <linux/pm_runtime.h>
> #include <media/v4l2-fwnode.h>
>
> #include "rkisp1-common.h"
>+#include "rkisp1-csi.h"
>
> /*
>  * ISP Details
>@@ -128,14 +128,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 	}
>
> 	s_asd->sd = sd;
>-	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
>-	if (IS_ERR(s_asd->dphy)) {
>-		if (PTR_ERR(s_asd->dphy) != -EPROBE_DEFER)
>-			dev_err(rkisp1->dev, "Couldn't get the MIPI D-PHY\n");
>-		return PTR_ERR(s_asd->dphy);
>-	}
>-
>-	phy_init(s_asd->dphy);
>
> 	/* Create the link to the sensor. */
> 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
>@@ -152,16 +144,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> }
>
>-static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
>-					  struct v4l2_subdev *sd,
>-					  struct v4l2_async_subdev *asd)
>-{
>-	struct rkisp1_sensor_async *s_asd =
>-		container_of(asd, struct rkisp1_sensor_async, asd);
>-
>-	phy_exit(s_asd->dphy);
>-}
>-
> static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> {
> 	struct rkisp1_device *rkisp1 =
>@@ -180,7 +162,6 @@ static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
>
> static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> 	.bound = rkisp1_subdev_notifier_bound,
>-	.unbind = rkisp1_subdev_notifier_unbind,
> 	.complete = rkisp1_subdev_notifier_complete,
> 	.destroy = rkisp1_subdev_notifier_destroy,
> };
>@@ -540,14 +521,20 @@ static int rkisp1_probe(struct platform_device *pdev)
> 		goto err_unreg_v4l2_dev;
> 	}
>
>-	ret = rkisp1_entities_register(rkisp1);
>+	ret = rkisp1_csi_init(rkisp1);
> 	if (ret)
> 		goto err_unreg_media_dev;
>
>+	ret = rkisp1_entities_register(rkisp1);
>+	if (ret)
>+		goto err_cleanup_csi;
>+
> 	rkisp1_debug_init(rkisp1);
>
> 	return 0;
>
>+err_cleanup_csi:
>+	rkisp1_csi_cleanup(rkisp1);
> err_unreg_media_dev:
> 	media_device_unregister(&rkisp1->media_dev);
> err_unreg_v4l2_dev:
>@@ -565,6 +552,7 @@ static int rkisp1_remove(struct platform_device *pdev)
> 	v4l2_async_nf_cleanup(&rkisp1->notifier);
>
> 	rkisp1_entities_unregister(rkisp1);
>+	rkisp1_csi_cleanup(rkisp1);
> 	rkisp1_debug_cleanup(rkisp1);
>
> 	media_device_unregister(&rkisp1->media_dev);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 81138c676ac0..5eabb321e320 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -9,8 +9,6 @@
>  */
>
> #include <linux/iopoll.h>
>-#include <linux/phy/phy.h>
>-#include <linux/phy/phy-mipi-dphy.h>
> #include <linux/pm_runtime.h>
> #include <linux/videodev2.h>
> #include <linux/vmalloc.h>
>@@ -18,6 +16,7 @@
> #include <media/v4l2-event.h>
>
> #include "rkisp1-common.h"
>+#include "rkisp1-csi.h"
>
> #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
>@@ -265,55 +264,6 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> 	return 0;
> }
>
>-static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
>-{
>-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>-	unsigned int lanes = rkisp1->active_sensor->lanes;
>-	u32 mipi_ctrl;
>-
>-	if (lanes < 1 || lanes > 4)
>-		return -EINVAL;
>-
>-	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
>-		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
>-		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
>-		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
>-
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
>-
>-	/* V12 could also use a newer csi2-host, but we don't want that yet */
>-	if (rkisp1->info->isp_ver == RKISP1_V12)
>-		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
>-
>-	/* Configure Data Type and Virtual Channel */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
>-		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
>-		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
>-
>-	/* Clear MIPI interrupts */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>-	/*
>-	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
>-	 * isp bus may be dead when switch isp.
>-	 */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>-		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
>-		     RKISP1_CIF_MIPI_ERR_DPHY |
>-		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
>-		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
>-
>-	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
>-		"  MIPI_IMG_DATA_SEL 0x%08x\n"
>-		"  MIPI_STATUS 0x%08x\n"
>-		"  MIPI_IMSC 0x%08x\n",
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
>-		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
>-
>-	return 0;
>-}
>-
> /* Configure MUX */
> static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> {
>@@ -326,7 +276,7 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> 		ret = rkisp1_config_dvp(rkisp1);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>-		ret = rkisp1_config_mipi(rkisp1);
>+		ret = rkisp1_config_mipi(&rkisp1->csi);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}
>
>@@ -360,17 +310,14 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> 	 * Stop ISP(isp) ->wait for ISP isp off
> 	 */
> 	/* stop and clear MI, MIPI, and ISP interrupts */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>-
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+
>+	rkisp1_mipi_stop(&rkisp1->csi);
>+
> 	/* stop ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
>@@ -417,11 +364,9 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> 	rkisp1_config_clk(rkisp1);
>
> 	/* Activate MIPI */
>-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-			     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>-	}
>+	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
>+		rkisp1_mipi_start(&rkisp1->csi);
>+
> 	/* Activate ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
>@@ -814,35 +759,6 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
>  * Stream operations
>  */
>
>-static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
>-				  struct rkisp1_sensor_async *sensor)
>-{
>-	struct rkisp1_device *rkisp1 =
>-		container_of(isp->sd.v4l2_dev, struct rkisp1_device, v4l2_dev);
>-	union phy_configure_opts opts;
>-	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
>-	s64 pixel_clock;
>-
>-	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
>-	if (!pixel_clock) {
>-		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
>-		return -EINVAL;
>-	}
>-
>-	phy_mipi_dphy_get_default_config(pixel_clock, isp->sink_fmt->bus_width,
>-					 sensor->lanes, cfg);
>-	phy_set_mode(sensor->dphy, PHY_MODE_MIPI_DPHY);
>-	phy_configure(sensor->dphy, &opts);
>-	phy_power_on(sensor->dphy);
>-
>-	return 0;
>-}
>-
>-static void rkisp1_mipi_csi2_stop(struct rkisp1_sensor_async *sensor)
>-{
>-	phy_power_off(sensor->dphy);
>-}
>-
> static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_device *rkisp1 =
>@@ -856,7 +772,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 				 false);
>
> 		rkisp1_isp_stop(rkisp1);
>-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
>+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> 		return 0;
> 	}
>
>@@ -878,7 +794,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	if (ret)
> 		goto mutex_unlock;
>
>-	ret = rkisp1_mipi_csi2_start(&rkisp1->isp, rkisp1->active_sensor);
>+	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
> 	if (ret)
> 		goto mutex_unlock;
>
>@@ -888,7 +804,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 			       true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
>-		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
>+		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>
>@@ -993,53 +909,6 @@ void rkisp1_isp_unregister(struct rkisp1_device *rkisp1)
>  * Interrupt handlers
>  */
>
>-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>-{
>-	struct device *dev = ctx;
>-	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
>-	u32 val, status;
>-
>-	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
>-	if (!status)
>-		return IRQ_NONE;
>-
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
>-
>-	/*
>-	 * Disable DPHY errctrl interrupt, because this dphy
>-	 * erctrl signal is asserted until the next changes
>-	 * of line state. This time is may be too long and cpu
>-	 * is hold in this interrupt.
>-	 */
>-	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
>-		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>-		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
>-			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
>-		rkisp1->isp.is_dphy_errctrl_disabled = true;
>-	}
>-
>-	/*
>-	 * Enable DPHY errctrl interrupt again, if mipi have receive
>-	 * the whole frame without any error.
>-	 */
>-	if (status == RKISP1_CIF_MIPI_FRAME_END) {
>-		/*
>-		 * Enable DPHY errctrl interrupt again, if mipi have receive
>-		 * the whole frame without any error.
>-		 */
>-		if (rkisp1->isp.is_dphy_errctrl_disabled) {
>-			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
>-			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
>-			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
>-			rkisp1->isp.is_dphy_errctrl_disabled = false;
>-		}
>-	} else {
>-		rkisp1->debug.mipi_error++;
>-	}
>-
>-	return IRQ_HANDLED;
>-}
>-
> static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
> {
> 	struct v4l2_event event = {
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 19/55] media: rkisp1: isp: Start CSI-2 receiver before ISP
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  3:51     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  3:51 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Make sure the ISP is ready to receive data before starting the CSI-2
>receiver by starting it first. Similarly, stop the CSI-2 receiver before
>the ISP when stopping streaming.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 11 +++++++----
> 1 file changed, 7 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 5eabb321e320..0e68c8d53404 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -771,8 +771,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
> 				 false);
>
>-		rkisp1_isp_stop(rkisp1);
> 		rkisp1_mipi_csi2_stop(&rkisp1->csi);
>+		rkisp1_isp_stop(rkisp1);
>+
> 		return 0;
> 	}
>
>@@ -794,11 +795,13 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	if (ret)
> 		goto mutex_unlock;
>
>+	rkisp1_isp_start(rkisp1);
>+
> 	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
>-	if (ret)
>+	if (ret) {
>+		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
>-
>-	rkisp1_isp_start(rkisp1);
>+	}
>
> 	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
> 			       true);
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 19/55] media: rkisp1: isp: Start CSI-2 receiver before ISP
@ 2022-06-25  3:51     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  3:51 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Make sure the ISP is ready to receive data before starting the CSI-2
>receiver by starting it first. Similarly, stop the CSI-2 receiver before
>the ISP when stopping streaming.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 11 +++++++----
> 1 file changed, 7 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 5eabb321e320..0e68c8d53404 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -771,8 +771,9 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
> 				 false);
>
>-		rkisp1_isp_stop(rkisp1);
> 		rkisp1_mipi_csi2_stop(&rkisp1->csi);
>+		rkisp1_isp_stop(rkisp1);
>+
> 		return 0;
> 	}
>
>@@ -794,11 +795,13 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	if (ret)
> 		goto mutex_unlock;
>
>+	rkisp1_isp_start(rkisp1);
>+
> 	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
>-	if (ret)
>+	if (ret) {
>+		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
>-
>-	rkisp1_isp_start(rkisp1);
>+	}
>
> 	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
> 			       true);
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 20/55] media: rkisp1: csi: Handle CSI-2 RX configuration fully in rkisp1-csi.c
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:00     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP layer now calls multiple functions of the CSI-2 RX layer to
>configure, start and stop it, with the steps for the last two
>operations. Move those calls to rkisp1_mipi_csi2_start() and
>rkisp1_mipi_csi2_stop() to simplify the ISP code and the API exposed by
>the CSI-2 receiver component.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 59 +++++++++++--------
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  4 --
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 10 +---
> 3 files changed, 35 insertions(+), 38 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 4af04296b625..f19513a601e8 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -18,7 +18,7 @@
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>-int rkisp1_config_mipi(struct rkisp1_csi *csi)
>+static int rkisp1_config_mipi(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>@@ -68,6 +68,30 @@ int rkisp1_config_mipi(struct rkisp1_csi *csi)
> 	return 0;
> }
>
>+void rkisp1_mipi_start(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>+}
>+
>+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	/* Mask and clear interrupts. */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+}
>+
> int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 			   struct rkisp1_sensor_async *sensor)
> {
>@@ -75,6 +99,11 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	union phy_configure_opts opts;
> 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> 	s64 pixel_clock;
>+	int ret;
>+
>+	ret = rkisp1_config_mipi(csi);
>+	if (ret)
>+		return ret;
>
> 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> 	if (!pixel_clock) {
>@@ -89,36 +118,16 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	phy_configure(csi->dphy, &opts);
> 	phy_power_on(csi->dphy);
>
>+	rkisp1_mipi_start(csi);
>+
> 	return 0;
> }
>
> void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
> {
>-	phy_power_off(csi->dphy);
>-}
>-
>-void rkisp1_mipi_start(struct rkisp1_csi *csi)
>-{
>-	struct rkisp1_device *rkisp1 = csi->rkisp1;
>-	u32 val;
>+	rkisp1_mipi_stop(csi);
>
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>-}
>-
>-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>-{
>-	struct rkisp1_device *rkisp1 = csi->rkisp1;
>-	u32 val;
>-
>-	/* Mask and clear interrupts. */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>-
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+	phy_power_off(csi->dphy);
> }
>
> irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index d97a4ee5c002..1f921d534865 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -17,12 +17,8 @@ struct rkisp1_sensor_async;
> int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
>-int rkisp1_config_mipi(struct rkisp1_csi *csi);
>-
> int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 			   struct rkisp1_sensor_async *sensor);
> void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
>-void rkisp1_mipi_start(struct rkisp1_csi *csi);
>-void rkisp1_mipi_stop(struct rkisp1_csi *csi);
>
> #endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 0e68c8d53404..208c68aa52ea 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -276,7 +276,6 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> 		ret = rkisp1_config_dvp(rkisp1);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>-		ret = rkisp1_config_mipi(&rkisp1->csi);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}
>
>@@ -309,15 +308,13 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> 	 * ISP(mi) stop in mi frame end -> Stop ISP(mipi) ->
> 	 * Stop ISP(isp) ->wait for ISP isp off
> 	 */
>-	/* stop and clear MI, MIPI, and ISP interrupts */
>+	/* stop and clear MI and ISP interrupts */
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
>
>-	rkisp1_mipi_stop(&rkisp1->csi);
>-
> 	/* stop ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
>@@ -358,15 +355,10 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
>
> static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> {
>-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
> 	u32 val;
>
> 	rkisp1_config_clk(rkisp1);
>
>-	/* Activate MIPI */
>-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
>-		rkisp1_mipi_start(&rkisp1->csi);
>-
> 	/* Activate ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 20/55] media: rkisp1: csi: Handle CSI-2 RX configuration fully in rkisp1-csi.c
@ 2022-06-25  4:00     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP layer now calls multiple functions of the CSI-2 RX layer to
>configure, start and stop it, with the steps for the last two
>operations. Move those calls to rkisp1_mipi_csi2_start() and
>rkisp1_mipi_csi2_stop() to simplify the ISP code and the API exposed by
>the CSI-2 receiver component.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 59 +++++++++++--------
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  4 --
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 10 +---
> 3 files changed, 35 insertions(+), 38 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 4af04296b625..f19513a601e8 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -18,7 +18,7 @@
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>-int rkisp1_config_mipi(struct rkisp1_csi *csi)
>+static int rkisp1_config_mipi(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>@@ -68,6 +68,30 @@ int rkisp1_config_mipi(struct rkisp1_csi *csi)
> 	return 0;
> }
>
>+void rkisp1_mipi_start(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>+}
>+
>+void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>+{
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	u32 val;
>+
>+	/* Mask and clear interrupts. */
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>+
>+	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>+	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>+		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+}
>+
> int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 			   struct rkisp1_sensor_async *sensor)
> {
>@@ -75,6 +99,11 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	union phy_configure_opts opts;
> 	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> 	s64 pixel_clock;
>+	int ret;
>+
>+	ret = rkisp1_config_mipi(csi);
>+	if (ret)
>+		return ret;
>
> 	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> 	if (!pixel_clock) {
>@@ -89,36 +118,16 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	phy_configure(csi->dphy, &opts);
> 	phy_power_on(csi->dphy);
>
>+	rkisp1_mipi_start(csi);
>+
> 	return 0;
> }
>
> void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
> {
>-	phy_power_off(csi->dphy);
>-}
>-
>-void rkisp1_mipi_start(struct rkisp1_csi *csi)
>-{
>-	struct rkisp1_device *rkisp1 = csi->rkisp1;
>-	u32 val;
>+	rkisp1_mipi_stop(csi);
>
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
>-}
>-
>-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>-{
>-	struct rkisp1_device *rkisp1 = csi->rkisp1;
>-	u32 val;
>-
>-	/* Mask and clear interrupts. */
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
>-
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
>-	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
>-		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
>+	phy_power_off(csi->dphy);
> }
>
> irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index d97a4ee5c002..1f921d534865 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -17,12 +17,8 @@ struct rkisp1_sensor_async;
> int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
>-int rkisp1_config_mipi(struct rkisp1_csi *csi);
>-
> int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 			   struct rkisp1_sensor_async *sensor);
> void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
>-void rkisp1_mipi_start(struct rkisp1_csi *csi);
>-void rkisp1_mipi_stop(struct rkisp1_csi *csi);
>
> #endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 0e68c8d53404..208c68aa52ea 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -276,7 +276,6 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> 		ret = rkisp1_config_dvp(rkisp1);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>-		ret = rkisp1_config_mipi(&rkisp1->csi);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}
>
>@@ -309,15 +308,13 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> 	 * ISP(mi) stop in mi frame end -> Stop ISP(mipi) ->
> 	 * Stop ISP(isp) ->wait for ISP isp off
> 	 */
>-	/* stop and clear MI, MIPI, and ISP interrupts */
>+	/* stop and clear MI and ISP interrupts */
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
> 	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
>
>-	rkisp1_mipi_stop(&rkisp1->csi);
>-
> 	/* stop ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
>@@ -358,15 +355,10 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
>
> static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> {
>-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
> 	u32 val;
>
> 	rkisp1_config_clk(rkisp1);
>
>-	/* Activate MIPI */
>-	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
>-		rkisp1_mipi_start(&rkisp1->csi);
>-
> 	/* Activate ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> 	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 21/55] media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi prefix
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:03     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:03 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The CSI-related functions are not named consistently. Fix it by using a
>common rkisp1_csi prefix.

this fixes my comment few patches back

>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +-
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 20 +++++++++----------
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 +++---
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |  4 ++--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     |  6 +++---
> 5 files changed, 19 insertions(+), 19 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index a52fa9e0dd66..dbf1baca623a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -555,7 +555,7 @@ void rkisp1_params_disable(struct rkisp1_params *params);
>
> /* irq handlers */
> irqreturn_t rkisp1_isp_isr(int irq, void *ctx);
>-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx);
>+irqreturn_t rkisp1_csi_isr(int irq, void *ctx);
> irqreturn_t rkisp1_capture_isr(int irq, void *ctx);
> void rkisp1_stats_isr(struct rkisp1_stats *stats, u32 isp_ris);
> void rkisp1_params_isr(struct rkisp1_device *rkisp1);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index f19513a601e8..c1bb8c05543d 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -18,7 +18,7 @@
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>-static int rkisp1_config_mipi(struct rkisp1_csi *csi)
>+static int rkisp1_csi_config(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>@@ -68,7 +68,7 @@ static int rkisp1_config_mipi(struct rkisp1_csi *csi)
> 	return 0;
> }
>
>-void rkisp1_mipi_start(struct rkisp1_csi *csi)
>+static void rkisp1_csi_enable(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	u32 val;
>@@ -78,7 +78,7 @@ void rkisp1_mipi_start(struct rkisp1_csi *csi)
> 		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
> }
>
>-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>+static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	u32 val;
>@@ -92,8 +92,8 @@ void rkisp1_mipi_stop(struct rkisp1_csi *csi)
> 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> }
>
>-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>-			   struct rkisp1_sensor_async *sensor)
>+int rkisp1_csi_start(struct rkisp1_csi *csi,
>+		     struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	union phy_configure_opts opts;
>@@ -101,7 +101,7 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	s64 pixel_clock;
> 	int ret;
>
>-	ret = rkisp1_config_mipi(csi);
>+	ret = rkisp1_csi_config(csi);
> 	if (ret)
> 		return ret;
>
>@@ -118,19 +118,19 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	phy_configure(csi->dphy, &opts);
> 	phy_power_on(csi->dphy);
>
>-	rkisp1_mipi_start(csi);
>+	rkisp1_csi_enable(csi);
>
> 	return 0;
> }
>
>-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
>+void rkisp1_csi_stop(struct rkisp1_csi *csi)
> {
>-	rkisp1_mipi_stop(csi);
>+	rkisp1_csi_disable(csi);
>
> 	phy_power_off(csi->dphy);
> }
>
>-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>+irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
> {
> 	struct device *dev = ctx;
> 	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index 1f921d534865..7d3f01cfb49f 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -17,8 +17,8 @@ struct rkisp1_sensor_async;
> int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
>-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>-			   struct rkisp1_sensor_async *sensor);
>-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
>+int rkisp1_csi_start(struct rkisp1_csi *csi,
>+		     struct rkisp1_sensor_async *sensor);
>+void rkisp1_csi_stop(struct rkisp1_csi *csi);
>
> #endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 373a1f00c10a..253220188abd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -383,7 +383,7 @@ static irqreturn_t rkisp1_isr(int irq, void *ctx)
> 	 */
> 	rkisp1_capture_isr(irq, ctx);
> 	rkisp1_isp_isr(irq, ctx);
>-	rkisp1_mipi_isr(irq, ctx);
>+	rkisp1_csi_isr(irq, ctx);
>
> 	return IRQ_HANDLED;
> }
>@@ -398,7 +398,7 @@ static const char * const px30_isp_clks[] = {
> static const struct rkisp1_isr_data px30_isp_isrs[] = {
> 	{ "isp", rkisp1_isp_isr },
> 	{ "mi", rkisp1_capture_isr },
>-	{ "mipi", rkisp1_mipi_isr },
>+	{ "mipi", rkisp1_csi_isr },
> };
>
> static const struct rkisp1_info px30_isp_info = {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 208c68aa52ea..ecb8ca0ad670 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -763,7 +763,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
> 				 false);
>
>-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
>+		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(rkisp1);
>
> 		return 0;
>@@ -789,7 +789,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	rkisp1_isp_start(rkisp1);
>
>-	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
>+	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
>@@ -799,7 +799,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 			       true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
>-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
>+		rkisp1_csi_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 21/55] media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi prefix
@ 2022-06-25  4:03     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:03 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The CSI-related functions are not named consistently. Fix it by using a
>common rkisp1_csi prefix.

this fixes my comment few patches back

>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 +-
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 20 +++++++++----------
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 +++---
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |  4 ++--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     |  6 +++---
> 5 files changed, 19 insertions(+), 19 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index a52fa9e0dd66..dbf1baca623a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -555,7 +555,7 @@ void rkisp1_params_disable(struct rkisp1_params *params);
>
> /* irq handlers */
> irqreturn_t rkisp1_isp_isr(int irq, void *ctx);
>-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx);
>+irqreturn_t rkisp1_csi_isr(int irq, void *ctx);
> irqreturn_t rkisp1_capture_isr(int irq, void *ctx);
> void rkisp1_stats_isr(struct rkisp1_stats *stats, u32 isp_ris);
> void rkisp1_params_isr(struct rkisp1_device *rkisp1);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index f19513a601e8..c1bb8c05543d 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -18,7 +18,7 @@
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>-static int rkisp1_config_mipi(struct rkisp1_csi *csi)
>+static int rkisp1_csi_config(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>@@ -68,7 +68,7 @@ static int rkisp1_config_mipi(struct rkisp1_csi *csi)
> 	return 0;
> }
>
>-void rkisp1_mipi_start(struct rkisp1_csi *csi)
>+static void rkisp1_csi_enable(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	u32 val;
>@@ -78,7 +78,7 @@ void rkisp1_mipi_start(struct rkisp1_csi *csi)
> 		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
> }
>
>-void rkisp1_mipi_stop(struct rkisp1_csi *csi)
>+static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	u32 val;
>@@ -92,8 +92,8 @@ void rkisp1_mipi_stop(struct rkisp1_csi *csi)
> 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> }
>
>-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>-			   struct rkisp1_sensor_async *sensor)
>+int rkisp1_csi_start(struct rkisp1_csi *csi,
>+		     struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	union phy_configure_opts opts;
>@@ -101,7 +101,7 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	s64 pixel_clock;
> 	int ret;
>
>-	ret = rkisp1_config_mipi(csi);
>+	ret = rkisp1_csi_config(csi);
> 	if (ret)
> 		return ret;
>
>@@ -118,19 +118,19 @@ int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> 	phy_configure(csi->dphy, &opts);
> 	phy_power_on(csi->dphy);
>
>-	rkisp1_mipi_start(csi);
>+	rkisp1_csi_enable(csi);
>
> 	return 0;
> }
>
>-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
>+void rkisp1_csi_stop(struct rkisp1_csi *csi)
> {
>-	rkisp1_mipi_stop(csi);
>+	rkisp1_csi_disable(csi);
>
> 	phy_power_off(csi->dphy);
> }
>
>-irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
>+irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
> {
> 	struct device *dev = ctx;
> 	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index 1f921d534865..7d3f01cfb49f 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -17,8 +17,8 @@ struct rkisp1_sensor_async;
> int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
>-int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
>-			   struct rkisp1_sensor_async *sensor);
>-void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
>+int rkisp1_csi_start(struct rkisp1_csi *csi,
>+		     struct rkisp1_sensor_async *sensor);
>+void rkisp1_csi_stop(struct rkisp1_csi *csi);
>
> #endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 373a1f00c10a..253220188abd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -383,7 +383,7 @@ static irqreturn_t rkisp1_isr(int irq, void *ctx)
> 	 */
> 	rkisp1_capture_isr(irq, ctx);
> 	rkisp1_isp_isr(irq, ctx);
>-	rkisp1_mipi_isr(irq, ctx);
>+	rkisp1_csi_isr(irq, ctx);
>
> 	return IRQ_HANDLED;
> }
>@@ -398,7 +398,7 @@ static const char * const px30_isp_clks[] = {
> static const struct rkisp1_isr_data px30_isp_isrs[] = {
> 	{ "isp", rkisp1_isp_isr },
> 	{ "mi", rkisp1_capture_isr },
>-	{ "mipi", rkisp1_mipi_isr },
>+	{ "mipi", rkisp1_csi_isr },
> };
>
> static const struct rkisp1_info px30_isp_info = {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 208c68aa52ea..ecb8ca0ad670 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -763,7 +763,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
> 				 false);
>
>-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
>+		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(rkisp1);
>
> 		return 0;
>@@ -789,7 +789,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	rkisp1_isp_start(rkisp1);
>
>-	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
>+	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
>@@ -799,7 +799,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 			       true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
>-		rkisp1_mipi_csi2_stop(&rkisp1->csi);
>+		rkisp1_csi_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 22/55] media: rkisp1: csi: Move start delay to rkisp1_csi_start()
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:05     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:05 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The delay in rkisp1_isp_start() is related to to the CSI-2 receiver and
>the camera sensor. Move it where it belongs, to rkisp1_csi_start().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 +++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 6 ------
> 2 files changed, 7 insertions(+), 6 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index c1bb8c05543d..fcaffffd371b 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -9,6 +9,7 @@
>  * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
>  */
>
>+#include <linux/delay.h>
> #include <linux/device.h>
> #include <linux/phy/phy.h>
> #include <linux/phy/phy-mipi-dphy.h>
>@@ -120,6 +121,12 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
>
> 	rkisp1_csi_enable(csi);
>
>+	/*
>+	 * CIF spec says to wait for sufficient time after enabling
>+	 * the MIPI interface and before starting the sensor output.
>+	 */
>+	usleep_range(1000, 1200);
>+
> 	return 0;
> }
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index ecb8ca0ad670..3ea0deb6b792 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -365,12 +365,6 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> 	       RKISP1_CIF_ISP_CTRL_ISP_ENABLE |
> 	       RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE;
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, val);
>-
>-	/*
>-	 * CIF spec says to wait for sufficient time after enabling
>-	 * the MIPI interface and before starting the sensor output.
>-	 */
>-	usleep_range(1000, 1200);
> }
>
> /* ----------------------------------------------------------------------------
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 22/55] media: rkisp1: csi: Move start delay to rkisp1_csi_start()
@ 2022-06-25  4:05     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:05 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The delay in rkisp1_isp_start() is related to to the CSI-2 receiver and
>the camera sensor. Move it where it belongs, to rkisp1_csi_start().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 +++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 6 ------
> 2 files changed, 7 insertions(+), 6 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index c1bb8c05543d..fcaffffd371b 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -9,6 +9,7 @@
>  * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
>  */
>
>+#include <linux/delay.h>
> #include <linux/device.h>
> #include <linux/phy/phy.h>
> #include <linux/phy/phy-mipi-dphy.h>
>@@ -120,6 +121,12 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
>
> 	rkisp1_csi_enable(csi);
>
>+	/*
>+	 * CIF spec says to wait for sufficient time after enabling
>+	 * the MIPI interface and before starting the sensor output.
>+	 */
>+	usleep_range(1000, 1200);
>+
> 	return 0;
> }
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index ecb8ca0ad670..3ea0deb6b792 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -365,12 +365,6 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> 	       RKISP1_CIF_ISP_CTRL_ISP_ENABLE |
> 	       RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE;
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, val);
>-
>-	/*
>-	 * CIF spec says to wait for sufficient time after enabling
>-	 * the MIPI interface and before starting the sensor output.
>-	 */
>-	usleep_range(1000, 1200);
> }
>
> /* ----------------------------------------------------------------------------
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 23/55] media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:28     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:28 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>To prepare for the removal of the active_sensor field from the
>rkisp1_device structure, pass the sensor pointer to the
>rkisp1_csi_config() function instead of accessing it through
>active_sensor.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 ++++---
> 1 file changed, 4 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index fcaffffd371b..925274b9a3c4 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -19,11 +19,12 @@
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>-static int rkisp1_csi_config(struct rkisp1_csi *csi)
>+static int rkisp1_csi_config(struct rkisp1_csi *csi,
>+			     struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>-	unsigned int lanes = rkisp1->active_sensor->lanes;
>+	unsigned int lanes = sensor->lanes;
> 	u32 mipi_ctrl;
>
> 	if (lanes < 1 || lanes > 4)
>@@ -102,7 +103,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
> 	s64 pixel_clock;
> 	int ret;
>
>-	ret = rkisp1_csi_config(csi);
>+	ret = rkisp1_csi_config(csi, sensor);
> 	if (ret)
> 		return ret;
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 23/55] media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config()
@ 2022-06-25  4:28     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:28 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>To prepare for the removal of the active_sensor field from the
>rkisp1_device structure, pass the sensor pointer to the
>rkisp1_csi_config() function instead of accessing it through
>active_sensor.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 7 ++++---
> 1 file changed, 4 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index fcaffffd371b..925274b9a3c4 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -19,11 +19,12 @@
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>-static int rkisp1_csi_config(struct rkisp1_csi *csi)
>+static int rkisp1_csi_config(struct rkisp1_csi *csi,
>+			     struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>-	unsigned int lanes = rkisp1->active_sensor->lanes;
>+	unsigned int lanes = sensor->lanes;
> 	u32 mipi_ctrl;
>
> 	if (lanes < 1 || lanes > 4)
>@@ -102,7 +103,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
> 	s64 pixel_clock;
> 	int ret;
>
>-	ret = rkisp1_csi_config(csi);
>+	ret = rkisp1_csi_config(csi, sensor);
> 	if (ret)
> 		return ret;
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 24/55] media: rkisp1: csi: Constify argument to rkisp1_csi_start()
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:29     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:29 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The sensor argument to rkisp1_csi_start() isn't meant to be modified by
>the function. Make it const.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 4 ++--
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h | 2 +-
> 2 files changed, 3 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 925274b9a3c4..425a3b014089 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -20,7 +20,7 @@
> #include "rkisp1-csi.h"
>
> static int rkisp1_csi_config(struct rkisp1_csi *csi,
>-			     struct rkisp1_sensor_async *sensor)
>+			     const struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>@@ -95,7 +95,7 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> }
>
> int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     struct rkisp1_sensor_async *sensor)
>+		     const struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	union phy_configure_opts opts;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index 7d3f01cfb49f..97ce7e7959ab 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -18,7 +18,7 @@ int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
> int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     struct rkisp1_sensor_async *sensor);
>+		     const struct rkisp1_sensor_async *sensor);
> void rkisp1_csi_stop(struct rkisp1_csi *csi);
>
> #endif /* _RKISP1_CSI_H */
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 24/55] media: rkisp1: csi: Constify argument to rkisp1_csi_start()
@ 2022-06-25  4:29     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:29 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The sensor argument to rkisp1_csi_start() isn't meant to be modified by
>the function. Make it const.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c | 4 ++--
> drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h | 2 +-
> 2 files changed, 3 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 925274b9a3c4..425a3b014089 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -20,7 +20,7 @@
> #include "rkisp1-csi.h"
>
> static int rkisp1_csi_config(struct rkisp1_csi *csi,
>-			     struct rkisp1_sensor_async *sensor)
>+			     const struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>@@ -95,7 +95,7 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> }
>
> int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     struct rkisp1_sensor_async *sensor)
>+		     const struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	union phy_configure_opts opts;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index 7d3f01cfb49f..97ce7e7959ab 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -18,7 +18,7 @@ int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
> int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     struct rkisp1_sensor_async *sensor);
>+		     const struct rkisp1_sensor_async *sensor);
> void rkisp1_csi_stop(struct rkisp1_csi *csi);
>
> #endif /* _RKISP1_CSI_H */
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 26/55] media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:32     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:32 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>To prepare for the removal of the active_sensor field from the
>rkisp1_device structure, pass the media bus type of flag to the
>rkisp1_config_cif() function instead of accessing them through
>active_sensor.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 44 +++++++++----------
> 1 file changed, 22 insertions(+), 22 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index a234cf29ec67..f6d1c93dd99d 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -136,15 +136,14 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
> /*
>  * configure ISP blocks with input format, size......
>  */
>-static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
>+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
>-	struct rkisp1_sensor_async *sensor;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>
>-	sensor = rkisp1->active_sensor;
> 	sink_fmt = rkisp1->isp.sink_fmt;
> 	src_fmt = rkisp1->isp.src_fmt;
> 	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
>@@ -157,7 +156,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> 	if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
> 		acq_mult = 1;
> 		if (src_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
>-			if (sensor->mbus_type == V4L2_MBUS_BT656)
>+			if (mbus_type == V4L2_MBUS_BT656)
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT_ITU656;
> 			else
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT;
>@@ -165,17 +164,17 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> 			rkisp1_write(rkisp1, RKISP1_CIF_ISP_DEMOSAIC,
> 				     RKISP1_CIF_ISP_DEMOSAIC_TH(0xc));
>
>-			if (sensor->mbus_type == V4L2_MBUS_BT656)
>+			if (mbus_type == V4L2_MBUS_BT656)
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU656;
> 			else
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU601;
> 		}
> 	} else if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_YUV) {
> 		acq_mult = 2;
>-		if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>+		if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 			isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
> 		} else {
>-			if (sensor->mbus_type == V4L2_MBUS_BT656)
>+			if (mbus_type == V4L2_MBUS_BT656)
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU656;
> 			else
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
>@@ -185,17 +184,16 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> 	}
>
> 	/* Set up input acquisition properties */
>-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
>-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
>-		if (sensor->mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
>+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
>+		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
> 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
> 	}
>
>-	if (sensor->mbus_type == V4L2_MBUS_PARALLEL) {
>-		if (sensor->mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
>+	if (mbus_type == V4L2_MBUS_PARALLEL) {
>+		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
> 			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
>
>-		if (sensor->mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
>+		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
> 			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
> 	}
>
>@@ -265,17 +263,17 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> }
>
> /* Configure MUX */
>-static int rkisp1_config_path(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_path(struct rkisp1_device *rkisp1,
>+			      enum v4l2_mbus_type mbus_type)
> {
>-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
> 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
> 	int ret = 0;
>
>-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
>-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
>+	if (mbus_type == V4L2_MBUS_BT656 ||
>+	    mbus_type == V4L2_MBUS_PARALLEL) {
> 		ret = rkisp1_config_dvp(rkisp1);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
>-	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>+	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}
>
>@@ -285,14 +283,15 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> }
>
> /* Hardware configure Entry */
>-static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
>+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	int ret;
>
>-	ret = rkisp1_config_isp(rkisp1);
>+	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
> 	if (ret)
> 		return ret;
>-	ret = rkisp1_config_path(rkisp1);
>+	ret = rkisp1_config_path(rkisp1, mbus_type);
> 	if (ret)
> 		return ret;
> 	rkisp1_config_ism(rkisp1);
>@@ -777,7 +776,8 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	rkisp1->isp.frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1);
>+	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
>+				rkisp1->active_sensor->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 26/55] media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif()
@ 2022-06-25  4:32     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:32 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>To prepare for the removal of the active_sensor field from the
>rkisp1_device structure, pass the media bus type of flag to the
>rkisp1_config_cif() function instead of accessing them through
>active_sensor.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 44 +++++++++----------
> 1 file changed, 22 insertions(+), 22 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index a234cf29ec67..f6d1c93dd99d 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -136,15 +136,14 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
> /*
>  * configure ISP blocks with input format, size......
>  */
>-static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
>+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
>-	struct rkisp1_sensor_async *sensor;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>
>-	sensor = rkisp1->active_sensor;
> 	sink_fmt = rkisp1->isp.sink_fmt;
> 	src_fmt = rkisp1->isp.src_fmt;
> 	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
>@@ -157,7 +156,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> 	if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
> 		acq_mult = 1;
> 		if (src_fmt->pixel_enc == V4L2_PIXEL_ENC_BAYER) {
>-			if (sensor->mbus_type == V4L2_MBUS_BT656)
>+			if (mbus_type == V4L2_MBUS_BT656)
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT_ITU656;
> 			else
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_RAW_PICT;
>@@ -165,17 +164,17 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> 			rkisp1_write(rkisp1, RKISP1_CIF_ISP_DEMOSAIC,
> 				     RKISP1_CIF_ISP_DEMOSAIC_TH(0xc));
>
>-			if (sensor->mbus_type == V4L2_MBUS_BT656)
>+			if (mbus_type == V4L2_MBUS_BT656)
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU656;
> 			else
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_BAYER_ITU601;
> 		}
> 	} else if (sink_fmt->pixel_enc == V4L2_PIXEL_ENC_YUV) {
> 		acq_mult = 2;
>-		if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>+		if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 			isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
> 		} else {
>-			if (sensor->mbus_type == V4L2_MBUS_BT656)
>+			if (mbus_type == V4L2_MBUS_BT656)
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU656;
> 			else
> 				isp_ctrl = RKISP1_CIF_ISP_CTRL_ISP_MODE_ITU601;
>@@ -185,17 +184,16 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1)
> 	}
>
> 	/* Set up input acquisition properties */
>-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
>-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
>-		if (sensor->mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
>+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
>+		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
> 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
> 	}
>
>-	if (sensor->mbus_type == V4L2_MBUS_PARALLEL) {
>-		if (sensor->mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
>+	if (mbus_type == V4L2_MBUS_PARALLEL) {
>+		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
> 			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
>
>-		if (sensor->mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
>+		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
> 			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
> 	}
>
>@@ -265,17 +263,17 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> }
>
> /* Configure MUX */
>-static int rkisp1_config_path(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_path(struct rkisp1_device *rkisp1,
>+			      enum v4l2_mbus_type mbus_type)
> {
>-	struct rkisp1_sensor_async *sensor = rkisp1->active_sensor;
> 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
> 	int ret = 0;
>
>-	if (sensor->mbus_type == V4L2_MBUS_BT656 ||
>-	    sensor->mbus_type == V4L2_MBUS_PARALLEL) {
>+	if (mbus_type == V4L2_MBUS_BT656 ||
>+	    mbus_type == V4L2_MBUS_PARALLEL) {
> 		ret = rkisp1_config_dvp(rkisp1);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
>-	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
>+	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}
>
>@@ -285,14 +283,15 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> }
>
> /* Hardware configure Entry */
>-static int rkisp1_config_cif(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
>+			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	int ret;
>
>-	ret = rkisp1_config_isp(rkisp1);
>+	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
> 	if (ret)
> 		return ret;
>-	ret = rkisp1_config_path(rkisp1);
>+	ret = rkisp1_config_path(rkisp1, mbus_type);
> 	if (ret)
> 		return ret;
> 	rkisp1_config_ism(rkisp1);
>@@ -777,7 +776,8 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	rkisp1->isp.frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1);
>+	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
>+				rkisp1->active_sensor->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 25/55] media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-25  4:46     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:46 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ret variable doesn't need to be initialized in
>rkisp1_isp_s_stream().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 3ea0deb6b792..a234cf29ec67 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -751,7 +751,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = &rkisp1->isp;
> 	struct v4l2_subdev *sensor_sd;
>-	int ret = 0;
>+	int ret;
>
> 	if (!enable) {
> 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 25/55] media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream()
@ 2022-06-25  4:46     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:46 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ret variable doesn't need to be initialized in
>rkisp1_isp_s_stream().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 3ea0deb6b792..a234cf29ec67 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -751,7 +751,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = &rkisp1->isp;
> 	struct v4l2_subdev *sensor_sd;
>-	int ret = 0;
>+	int ret;
>
> 	if (!enable) {
> 		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 28/55] media: rkisp1: isp: Add container_of wrapper to cast subdev to rkisp1_isp
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  4:48     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:48 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Replace manual container_of() calls with a static inline wrapper to
>increase readability.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-isp.c   | 15 ++++++++++-----
> 1 file changed, 10 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 4f12fc0b7694..812fb2ea5323 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -370,6 +370,11 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
>  * Subdev pad operations
>  */
>
>+static inline struct rkisp1_isp *to_rkisp1_isp(struct v4l2_subdev *sd)
>+{
>+	return container_of(sd, struct rkisp1_isp, sd);
>+}
>+
> static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
> 				     struct v4l2_subdev_state *sd_state,
> 				     struct v4l2_subdev_mbus_code_enum *code)
>@@ -625,7 +630,7 @@ static int rkisp1_isp_get_fmt(struct v4l2_subdev *sd,
> 			      struct v4l2_subdev_state *sd_state,
> 			      struct v4l2_subdev_format *fmt)
> {
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>
> 	mutex_lock(&isp->ops_lock);
> 	fmt->format = *rkisp1_isp_get_pad_fmt(isp, sd_state, fmt->pad,
>@@ -638,7 +643,7 @@ static int rkisp1_isp_set_fmt(struct v4l2_subdev *sd,
> 			      struct v4l2_subdev_state *sd_state,
> 			      struct v4l2_subdev_format *fmt)
> {
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>
> 	mutex_lock(&isp->ops_lock);
> 	if (fmt->pad == RKISP1_ISP_PAD_SINK_VIDEO)
>@@ -659,7 +664,7 @@ static int rkisp1_isp_get_selection(struct v4l2_subdev *sd,
> 				    struct v4l2_subdev_state *sd_state,
> 				    struct v4l2_subdev_selection *sel)
> {
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	int ret = 0;
>
> 	if (sel->pad != RKISP1_ISP_PAD_SOURCE_VIDEO &&
>@@ -701,7 +706,7 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
> {
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	int ret = 0;
>
> 	if (sel->target != V4L2_SEL_TGT_CROP)
>@@ -748,7 +753,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
>-	struct rkisp1_isp *isp = &rkisp1->isp;
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	struct rkisp1_sensor_async *asd;
> 	int ret;
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 28/55] media: rkisp1: isp: Add container_of wrapper to cast subdev to rkisp1_isp
@ 2022-06-25  4:48     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:48 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Replace manual container_of() calls with a static inline wrapper to
>increase readability.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-isp.c   | 15 ++++++++++-----
> 1 file changed, 10 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 4f12fc0b7694..812fb2ea5323 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -370,6 +370,11 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
>  * Subdev pad operations
>  */
>
>+static inline struct rkisp1_isp *to_rkisp1_isp(struct v4l2_subdev *sd)
>+{
>+	return container_of(sd, struct rkisp1_isp, sd);
>+}
>+
> static int rkisp1_isp_enum_mbus_code(struct v4l2_subdev *sd,
> 				     struct v4l2_subdev_state *sd_state,
> 				     struct v4l2_subdev_mbus_code_enum *code)
>@@ -625,7 +630,7 @@ static int rkisp1_isp_get_fmt(struct v4l2_subdev *sd,
> 			      struct v4l2_subdev_state *sd_state,
> 			      struct v4l2_subdev_format *fmt)
> {
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>
> 	mutex_lock(&isp->ops_lock);
> 	fmt->format = *rkisp1_isp_get_pad_fmt(isp, sd_state, fmt->pad,
>@@ -638,7 +643,7 @@ static int rkisp1_isp_set_fmt(struct v4l2_subdev *sd,
> 			      struct v4l2_subdev_state *sd_state,
> 			      struct v4l2_subdev_format *fmt)
> {
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>
> 	mutex_lock(&isp->ops_lock);
> 	if (fmt->pad == RKISP1_ISP_PAD_SINK_VIDEO)
>@@ -659,7 +664,7 @@ static int rkisp1_isp_get_selection(struct v4l2_subdev *sd,
> 				    struct v4l2_subdev_state *sd_state,
> 				    struct v4l2_subdev_selection *sel)
> {
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	int ret = 0;
>
> 	if (sel->pad != RKISP1_ISP_PAD_SOURCE_VIDEO &&
>@@ -701,7 +706,7 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
> {
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
>-	struct rkisp1_isp *isp = container_of(sd, struct rkisp1_isp, sd);
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	int ret = 0;
>
> 	if (sel->target != V4L2_SEL_TGT_CROP)
>@@ -748,7 +753,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
>-	struct rkisp1_isp *isp = &rkisp1->isp;
>+	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	struct rkisp1_sensor_async *asd;
> 	int ret;
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 29/55] media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  4:50     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:50 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1_isp structure documentation mentions a backpointer field to
>rkisp1_device, but the field is missing. Add it, and use it to replace
>more complicated constructs using container_of() on the v4l2_device.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-common.h    |  1 +
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c   | 11 +++++------
> 2 files changed, 6 insertions(+), 6 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 7a6f55a31bb0..3c55e922346e 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -162,6 +162,7 @@ struct rkisp1_csi {
>  */
> struct rkisp1_isp {
> 	struct v4l2_subdev sd;
>+	struct rkisp1_device *rkisp1;
> 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
> 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
> 	const struct rkisp1_mbus_info *sink_fmt;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 812fb2ea5323..f8ab1d9cc8cd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -704,15 +704,13 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
> 				    struct v4l2_subdev_state *sd_state,
> 				    struct v4l2_subdev_selection *sel)
> {
>-	struct rkisp1_device *rkisp1 =
>-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	int ret = 0;
>
> 	if (sel->target != V4L2_SEL_TGT_CROP)
> 		return -EINVAL;
>
>-	dev_dbg(rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
>+	dev_dbg(isp->rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
> 		sel->pad, sel->r.left, sel->r.top, sel->r.width, sel->r.height);
> 	mutex_lock(&isp->ops_lock);
> 	if (sel->pad == RKISP1_ISP_PAD_SINK_VIDEO)
>@@ -751,9 +749,8 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
>
> static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
>-	struct rkisp1_device *rkisp1 =
>-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	struct rkisp1_sensor_async *asd;
> 	int ret;
>
>@@ -840,12 +837,14 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
> {
> 	struct v4l2_subdev_state state = {
> 		.pads = rkisp1->isp.pad_cfg
>-		};
>+	};
> 	struct rkisp1_isp *isp = &rkisp1->isp;
> 	struct media_pad *pads = isp->pads;
> 	struct v4l2_subdev *sd = &isp->sd;
> 	int ret;
>
>+	isp->rkisp1 = rkisp1;
>+
> 	v4l2_subdev_init(sd, &rkisp1_isp_ops);
> 	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE | V4L2_SUBDEV_FL_HAS_EVENTS;
> 	sd->entity.ops = &rkisp1_isp_media_ops;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 29/55] media: rkisp1: isp: Add rkisp1_device backpointer to rkisp1_isp
@ 2022-06-25  4:50     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:50 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1_isp structure documentation mentions a backpointer field to
>rkisp1_device, but the field is missing. Add it, and use it to replace
>more complicated constructs using container_of() on the v4l2_device.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-common.h    |  1 +
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c   | 11 +++++------
> 2 files changed, 6 insertions(+), 6 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 7a6f55a31bb0..3c55e922346e 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -162,6 +162,7 @@ struct rkisp1_csi {
>  */
> struct rkisp1_isp {
> 	struct v4l2_subdev sd;
>+	struct rkisp1_device *rkisp1;
> 	struct media_pad pads[RKISP1_ISP_PAD_MAX];
> 	struct v4l2_subdev_pad_config pad_cfg[RKISP1_ISP_PAD_MAX];
> 	const struct rkisp1_mbus_info *sink_fmt;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 812fb2ea5323..f8ab1d9cc8cd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -704,15 +704,13 @@ static int rkisp1_isp_set_selection(struct v4l2_subdev *sd,
> 				    struct v4l2_subdev_state *sd_state,
> 				    struct v4l2_subdev_selection *sel)
> {
>-	struct rkisp1_device *rkisp1 =
>-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	int ret = 0;
>
> 	if (sel->target != V4L2_SEL_TGT_CROP)
> 		return -EINVAL;
>
>-	dev_dbg(rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
>+	dev_dbg(isp->rkisp1->dev, "%s: pad: %d sel(%d,%d)/%dx%d\n", __func__,
> 		sel->pad, sel->r.left, sel->r.top, sel->r.width, sel->r.height);
> 	mutex_lock(&isp->ops_lock);
> 	if (sel->pad == RKISP1_ISP_PAD_SINK_VIDEO)
>@@ -751,9 +749,8 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
>
> static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
>-	struct rkisp1_device *rkisp1 =
>-		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	struct rkisp1_sensor_async *asd;
> 	int ret;
>
>@@ -840,12 +837,14 @@ int rkisp1_isp_register(struct rkisp1_device *rkisp1)
> {
> 	struct v4l2_subdev_state state = {
> 		.pads = rkisp1->isp.pad_cfg
>-		};
>+	};
> 	struct rkisp1_isp *isp = &rkisp1->isp;
> 	struct media_pad *pads = isp->pads;
> 	struct v4l2_subdev *sd = &isp->sd;
> 	int ret;
>
>+	isp->rkisp1 = rkisp1;
>+
> 	v4l2_subdev_init(sd, &rkisp1_isp_ops);
> 	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE | V4L2_SUBDEV_FL_HAS_EVENTS;
> 	sd->entity.ops = &rkisp1_isp_media_ops;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 30/55] media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  4:52     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:52 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Replace the rkisp1_device pointer argument to the internal functions of
>the ISP implementation with a rkisp1_isp object. This makes the code
>flow more logical, as the functions operate on the ISP object.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 60 +++++++++++--------
> 1 file changed, 34 insertions(+), 26 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f8ab1d9cc8cd..e27137b5c33e 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -109,12 +109,13 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
>  * This should only be called when configuring CIF
>  * or at the frame end interrupt
>  */
>-static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
>+static void rkisp1_config_ism(struct rkisp1_isp *isp)
> {
> 	struct v4l2_rect *src_crop =
>-		rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
>+		rkisp1_isp_get_pad_crop(isp, NULL,
> 					RKISP1_ISP_PAD_SOURCE_VIDEO,
> 					V4L2_SUBDEV_FORMAT_ACTIVE);
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 val;
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IS_RECENTER, 0);
>@@ -136,20 +137,21 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
> /*
>  * configure ISP blocks with input format, size......
>  */
>-static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
>+static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>
>-	sink_fmt = rkisp1->isp.sink_fmt;
>-	src_fmt = rkisp1->isp.src_fmt;
>-	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
>+	sink_fmt = isp->sink_fmt;
>+	src_fmt = isp->src_fmt;
>+	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
> 					  V4L2_SUBDEV_FORMAT_ACTIVE);
>-	sink_crop = rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
>+	sink_crop = rkisp1_isp_get_pad_crop(isp, NULL,
> 					    RKISP1_ISP_PAD_SINK_VIDEO,
> 					    V4L2_SUBDEV_FORMAT_ACTIVE);
>
>@@ -226,7 +228,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
> 	} else {
> 		struct v4l2_mbus_framefmt *src_frm;
>
>-		src_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
>+		src_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 						 RKISP1_ISP_PAD_SINK_VIDEO,
> 						 V4L2_SUBDEV_FORMAT_ACTIVE);
> 		rkisp1_params_configure(&rkisp1->params, sink_fmt->bayer_pat,
>@@ -236,9 +238,10 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
> 	return 0;
> }
>
>-static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_dvp(struct rkisp1_isp *isp)
> {
>-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
>+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
> 	u32 val, input_sel;
>
> 	switch (sink_fmt->bus_width) {
>@@ -263,15 +266,16 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> }
>
> /* Configure MUX */
>-static int rkisp1_config_path(struct rkisp1_device *rkisp1,
>+static int rkisp1_config_path(struct rkisp1_isp *isp,
> 			      enum v4l2_mbus_type mbus_type)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
> 	int ret = 0;
>
> 	if (mbus_type == V4L2_MBUS_BT656 ||
> 	    mbus_type == V4L2_MBUS_PARALLEL) {
>-		ret = rkisp1_config_dvp(rkisp1);
>+		ret = rkisp1_config_dvp(isp);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
>@@ -283,24 +287,25 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1,
> }
>
> /* Hardware configure Entry */
>-static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
>+static int rkisp1_config_cif(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	int ret;
>
>-	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
>+	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
> 	if (ret)
> 		return ret;
>-	ret = rkisp1_config_path(rkisp1, mbus_type);
>+	ret = rkisp1_config_path(isp, mbus_type);
> 	if (ret)
> 		return ret;
>-	rkisp1_config_ism(rkisp1);
>+	rkisp1_config_ism(isp);
>
> 	return 0;
> }
>
>-static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
>+static void rkisp1_isp_stop(struct rkisp1_isp *isp)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 val;
>
> 	/*
>@@ -332,8 +337,10 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> 	rkisp1_write(rkisp1, RKISP1_CIF_VI_IRCL, 0x0);
> }
>
>-static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
>+static void rkisp1_config_clk(struct rkisp1_isp *isp)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
>+
> 	u32 val = RKISP1_CIF_VI_ICCL_ISP_CLK | RKISP1_CIF_VI_ICCL_CP_CLK |
> 		  RKISP1_CIF_VI_ICCL_MRSZ_CLK | RKISP1_CIF_VI_ICCL_SRSZ_CLK |
> 		  RKISP1_CIF_VI_ICCL_JPEG_CLK | RKISP1_CIF_VI_ICCL_MI_CLK |
>@@ -352,11 +359,12 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
> 	}
> }
>
>-static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
>+static void rkisp1_isp_start(struct rkisp1_isp *isp)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 val;
>
>-	rkisp1_config_clk(rkisp1);
>+	rkisp1_config_clk(isp);
>
> 	/* Activate ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
>@@ -758,7 +766,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>
> 		rkisp1_csi_stop(&rkisp1->csi);
>-		rkisp1_isp_stop(rkisp1);
>+		rkisp1_isp_stop(isp);
>
> 		return 0;
> 	}
>@@ -775,23 +783,23 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> 		return -EINVAL;
>
>-	rkisp1->isp.frame_sequence = -1;
>+	isp->frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
>+	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
>-	rkisp1_isp_start(rkisp1);
>+	rkisp1_isp_start(isp);
>
> 	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> 	if (ret) {
>-		rkisp1_isp_stop(rkisp1);
>+		rkisp1_isp_stop(isp);
> 		goto mutex_unlock;
> 	}
>
> 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 	if (ret) {
>-		rkisp1_isp_stop(rkisp1);
>+		rkisp1_isp_stop(isp);
> 		rkisp1_csi_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 30/55] media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions
@ 2022-06-25  4:52     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  4:52 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Replace the rkisp1_device pointer argument to the internal functions of
>the ISP implementation with a rkisp1_isp object. This makes the code
>flow more logical, as the functions operate on the ISP object.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 60 +++++++++++--------
> 1 file changed, 34 insertions(+), 26 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f8ab1d9cc8cd..e27137b5c33e 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -109,12 +109,13 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
>  * This should only be called when configuring CIF
>  * or at the frame end interrupt
>  */
>-static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
>+static void rkisp1_config_ism(struct rkisp1_isp *isp)
> {
> 	struct v4l2_rect *src_crop =
>-		rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
>+		rkisp1_isp_get_pad_crop(isp, NULL,
> 					RKISP1_ISP_PAD_SOURCE_VIDEO,
> 					V4L2_SUBDEV_FORMAT_ACTIVE);
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 val;
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IS_RECENTER, 0);
>@@ -136,20 +137,21 @@ static void rkisp1_config_ism(struct rkisp1_device *rkisp1)
> /*
>  * configure ISP blocks with input format, size......
>  */
>-static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
>+static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>
>-	sink_fmt = rkisp1->isp.sink_fmt;
>-	src_fmt = rkisp1->isp.src_fmt;
>-	sink_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
>+	sink_fmt = isp->sink_fmt;
>+	src_fmt = isp->src_fmt;
>+	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
> 					  V4L2_SUBDEV_FORMAT_ACTIVE);
>-	sink_crop = rkisp1_isp_get_pad_crop(&rkisp1->isp, NULL,
>+	sink_crop = rkisp1_isp_get_pad_crop(isp, NULL,
> 					    RKISP1_ISP_PAD_SINK_VIDEO,
> 					    V4L2_SUBDEV_FORMAT_ACTIVE);
>
>@@ -226,7 +228,7 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
> 	} else {
> 		struct v4l2_mbus_framefmt *src_frm;
>
>-		src_frm = rkisp1_isp_get_pad_fmt(&rkisp1->isp, NULL,
>+		src_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 						 RKISP1_ISP_PAD_SINK_VIDEO,
> 						 V4L2_SUBDEV_FORMAT_ACTIVE);
> 		rkisp1_params_configure(&rkisp1->params, sink_fmt->bayer_pat,
>@@ -236,9 +238,10 @@ static int rkisp1_config_isp(struct rkisp1_device *rkisp1,
> 	return 0;
> }
>
>-static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
>+static int rkisp1_config_dvp(struct rkisp1_isp *isp)
> {
>-	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
>+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
> 	u32 val, input_sel;
>
> 	switch (sink_fmt->bus_width) {
>@@ -263,15 +266,16 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> }
>
> /* Configure MUX */
>-static int rkisp1_config_path(struct rkisp1_device *rkisp1,
>+static int rkisp1_config_path(struct rkisp1_isp *isp,
> 			      enum v4l2_mbus_type mbus_type)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
> 	int ret = 0;
>
> 	if (mbus_type == V4L2_MBUS_BT656 ||
> 	    mbus_type == V4L2_MBUS_PARALLEL) {
>-		ret = rkisp1_config_dvp(rkisp1);
>+		ret = rkisp1_config_dvp(isp);
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
>@@ -283,24 +287,25 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1,
> }
>
> /* Hardware configure Entry */
>-static int rkisp1_config_cif(struct rkisp1_device *rkisp1,
>+static int rkisp1_config_cif(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	int ret;
>
>-	ret = rkisp1_config_isp(rkisp1, mbus_type, mbus_flags);
>+	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
> 	if (ret)
> 		return ret;
>-	ret = rkisp1_config_path(rkisp1, mbus_type);
>+	ret = rkisp1_config_path(isp, mbus_type);
> 	if (ret)
> 		return ret;
>-	rkisp1_config_ism(rkisp1);
>+	rkisp1_config_ism(isp);
>
> 	return 0;
> }
>
>-static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
>+static void rkisp1_isp_stop(struct rkisp1_isp *isp)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 val;
>
> 	/*
>@@ -332,8 +337,10 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> 	rkisp1_write(rkisp1, RKISP1_CIF_VI_IRCL, 0x0);
> }
>
>-static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
>+static void rkisp1_config_clk(struct rkisp1_isp *isp)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
>+
> 	u32 val = RKISP1_CIF_VI_ICCL_ISP_CLK | RKISP1_CIF_VI_ICCL_CP_CLK |
> 		  RKISP1_CIF_VI_ICCL_MRSZ_CLK | RKISP1_CIF_VI_ICCL_SRSZ_CLK |
> 		  RKISP1_CIF_VI_ICCL_JPEG_CLK | RKISP1_CIF_VI_ICCL_MI_CLK |
>@@ -352,11 +359,12 @@ static void rkisp1_config_clk(struct rkisp1_device *rkisp1)
> 	}
> }
>
>-static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
>+static void rkisp1_isp_start(struct rkisp1_isp *isp)
> {
>+	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 val;
>
>-	rkisp1_config_clk(rkisp1);
>+	rkisp1_config_clk(isp);
>
> 	/* Activate ISP */
> 	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
>@@ -758,7 +766,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>
> 		rkisp1_csi_stop(&rkisp1->csi);
>-		rkisp1_isp_stop(rkisp1);
>+		rkisp1_isp_stop(isp);
>
> 		return 0;
> 	}
>@@ -775,23 +783,23 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> 		return -EINVAL;
>
>-	rkisp1->isp.frame_sequence = -1;
>+	isp->frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
>+	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
>-	rkisp1_isp_start(rkisp1);
>+	rkisp1_isp_start(isp);
>
> 	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> 	if (ret) {
>-		rkisp1_isp_stop(rkisp1);
>+		rkisp1_isp_stop(isp);
> 		goto mutex_unlock;
> 	}
>
> 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 	if (ret) {
>-		rkisp1_isp_stop(rkisp1);
>+		rkisp1_isp_stop(isp);
> 		rkisp1_csi_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 31/55] media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  5:00     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP_ACQ_PROP register is set twice, once in rkisp1_config_isp() for
>most of its fields, and once in rkisp1_config_dvp() (called from
>rkisp1_config_path()) to configure the input selection field. Move the
>latter to rkisp1_config_isp() to write the register once only, and drop
>the now empty rkisp1_config_dvp() function.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 62 +++++++------------
> 1 file changed, 22 insertions(+), 40 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index e27137b5c33e..f5b8a2e31936 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
>+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>@@ -189,6 +189,21 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
> 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
> 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
>+
>+		switch (sink_fmt->bus_width) {
>+		case 8:
>+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
>+			break;
>+		case 10:
>+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
>+			break;
>+		case 12:
>+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
>+			break;
>+		default:
>+			dev_err(rkisp1->dev, "Invalid bus width\n");

maybe also print the bus width here

>+			return -EINVAL;
>+		}
> 	}
>
> 	if (mbus_type == V4L2_MBUS_PARALLEL) {
>@@ -201,7 +216,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
>-		     signal | sink_fmt->yuv_seq |
>+		     signal | sink_fmt->yuv_seq | input_sel |
> 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
> 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
>@@ -238,52 +253,20 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	return 0;
> }
>
>-static int rkisp1_config_dvp(struct rkisp1_isp *isp)
>-{
>-	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
>-	u32 val, input_sel;
>-
>-	switch (sink_fmt->bus_width) {
>-	case 8:
>-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
>-		break;
>-	case 10:
>-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
>-		break;
>-	case 12:
>-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
>-		break;
>-	default:
>-		dev_err(rkisp1->dev, "Invalid bus width\n");
>-		return -EINVAL;
>-	}
>-
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_ACQ_PROP);
>-	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP, val | input_sel);
>-
>-	return 0;
>-}
>-
> /* Configure MUX */
>-static int rkisp1_config_path(struct rkisp1_isp *isp,
>-			      enum v4l2_mbus_type mbus_type)
>+static void rkisp1_config_path(struct rkisp1_isp *isp,
>+			       enum v4l2_mbus_type mbus_type)
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
>-	int ret = 0;
>
>-	if (mbus_type == V4L2_MBUS_BT656 ||
>-	    mbus_type == V4L2_MBUS_PARALLEL) {
>-		ret = rkisp1_config_dvp(isp);
>+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}

can remove the curly braces

thanks,
Dafna

>
> 	rkisp1_write(rkisp1, RKISP1_CIF_VI_DPCL, dpcl);
>-
>-	return ret;
> }
>
> /* Hardware configure Entry */
>@@ -295,9 +278,8 @@ static int rkisp1_config_cif(struct rkisp1_isp *isp,
> 	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
> 	if (ret)
> 		return ret;
>-	ret = rkisp1_config_path(isp, mbus_type);
>-	if (ret)
>-		return ret;
>+
>+	rkisp1_config_path(isp, mbus_type);
> 	rkisp1_config_ism(isp);
>
> 	return 0;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 31/55] media: rkisp1: isp: Move input configuration to rkisp1_config_isp()
@ 2022-06-25  5:00     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The ISP_ACQ_PROP register is set twice, once in rkisp1_config_isp() for
>most of its fields, and once in rkisp1_config_dvp() (called from
>rkisp1_config_path()) to configure the input selection field. Move the
>latter to rkisp1_config_isp() to write the register once only, and drop
>the now empty rkisp1_config_dvp() function.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 62 +++++++------------
> 1 file changed, 22 insertions(+), 40 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index e27137b5c33e..f5b8a2e31936 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0;
>+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>@@ -189,6 +189,21 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
> 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
> 			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
>+
>+		switch (sink_fmt->bus_width) {
>+		case 8:
>+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
>+			break;
>+		case 10:
>+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
>+			break;
>+		case 12:
>+			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
>+			break;
>+		default:
>+			dev_err(rkisp1->dev, "Invalid bus width\n");

maybe also print the bus width here

>+			return -EINVAL;
>+		}
> 	}
>
> 	if (mbus_type == V4L2_MBUS_PARALLEL) {
>@@ -201,7 +216,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
>-		     signal | sink_fmt->yuv_seq |
>+		     signal | sink_fmt->yuv_seq | input_sel |
> 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
> 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
>@@ -238,52 +253,20 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	return 0;
> }
>
>-static int rkisp1_config_dvp(struct rkisp1_isp *isp)
>-{
>-	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
>-	u32 val, input_sel;
>-
>-	switch (sink_fmt->bus_width) {
>-	case 8:
>-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
>-		break;
>-	case 10:
>-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
>-		break;
>-	case 12:
>-		input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
>-		break;
>-	default:
>-		dev_err(rkisp1->dev, "Invalid bus width\n");
>-		return -EINVAL;
>-	}
>-
>-	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_ACQ_PROP);
>-	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP, val | input_sel);
>-
>-	return 0;
>-}
>-
> /* Configure MUX */
>-static int rkisp1_config_path(struct rkisp1_isp *isp,
>-			      enum v4l2_mbus_type mbus_type)
>+static void rkisp1_config_path(struct rkisp1_isp *isp,
>+			       enum v4l2_mbus_type mbus_type)
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 dpcl = rkisp1_read(rkisp1, RKISP1_CIF_VI_DPCL);
>-	int ret = 0;
>
>-	if (mbus_type == V4L2_MBUS_BT656 ||
>-	    mbus_type == V4L2_MBUS_PARALLEL) {
>-		ret = rkisp1_config_dvp(isp);
>+	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> 	} else if (mbus_type == V4L2_MBUS_CSI2_DPHY) {
> 		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> 	}

can remove the curly braces

thanks,
Dafna

>
> 	rkisp1_write(rkisp1, RKISP1_CIF_VI_DPCL, dpcl);
>-
>-	return ret;
> }
>
> /* Hardware configure Entry */
>@@ -295,9 +278,8 @@ static int rkisp1_config_cif(struct rkisp1_isp *isp,
> 	ret = rkisp1_config_isp(isp, mbus_type, mbus_flags);
> 	if (ret)
> 		return ret;
>-	ret = rkisp1_config_path(isp, mbus_type);
>-	if (ret)
>-		return ret;
>+
>+	rkisp1_config_path(isp, mbus_type);
> 	rkisp1_config_ism(isp);
>
> 	return 0;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 32/55] media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single variable
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  5:03     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:03 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1_config_isp() function stores the value of the input selection
>and polarity configuration in two different local variables, OR'ed
>together when writing the register. Merge them into a single acq_prop
>variable.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-isp.c  | 16 ++++++++--------
> 1 file changed, 8 insertions(+), 8 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f5b8a2e31936..4496af991c82 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
>+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>@@ -188,17 +188,17 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	/* Set up input acquisition properties */
> 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
> 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
>-			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
>
> 		switch (sink_fmt->bus_width) {
> 		case 8:
>-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
> 			break;
> 		case 10:
>-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
> 			break;
> 		case 12:
>-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
> 			break;
> 		default:
> 			dev_err(rkisp1->dev, "Invalid bus width\n");
>@@ -208,15 +208,15 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
>
> 	if (mbus_type == V4L2_MBUS_PARALLEL) {
> 		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
>-			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
>
> 		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
>-			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
> 	}
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
>-		     signal | sink_fmt->yuv_seq | input_sel |
>+		     acq_prop | sink_fmt->yuv_seq |
> 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
> 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 32/55] media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single variable
@ 2022-06-25  5:03     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:03 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The rkisp1_config_isp() function stores the value of the input selection
>and polarity configuration in two different local variables, OR'ed
>together when writing the register. Merge them into a single acq_prop
>variable.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../media/platform/rockchip/rkisp1/rkisp1-isp.c  | 16 ++++++++--------
> 1 file changed, 8 insertions(+), 8 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f5b8a2e31936..4496af991c82 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -141,7 +141,7 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 			     enum v4l2_mbus_type mbus_type, u32 mbus_flags)
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, signal = 0, input_sel = 0;
>+	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
> 	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>@@ -188,17 +188,17 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	/* Set up input acquisition properties */
> 	if (mbus_type == V4L2_MBUS_BT656 || mbus_type == V4L2_MBUS_PARALLEL) {
> 		if (mbus_flags & V4L2_MBUS_PCLK_SAMPLE_RISING)
>-			signal = RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_POS_EDGE;
>
> 		switch (sink_fmt->bus_width) {
> 		case 8:
>-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_8B_ZERO;
> 			break;
> 		case 10:
>-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_10B_ZERO;
> 			break;
> 		case 12:
>-			input_sel = RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_IN_SEL_12B;
> 			break;
> 		default:
> 			dev_err(rkisp1->dev, "Invalid bus width\n");
>@@ -208,15 +208,15 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
>
> 	if (mbus_type == V4L2_MBUS_PARALLEL) {
> 		if (mbus_flags & V4L2_MBUS_VSYNC_ACTIVE_LOW)
>-			signal |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_VSYNC_LOW;
>
> 		if (mbus_flags & V4L2_MBUS_HSYNC_ACTIVE_LOW)
>-			signal |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
>+			acq_prop |= RKISP1_CIF_ISP_ACQ_PROP_HSYNC_LOW;
> 	}
>
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_CTRL, isp_ctrl);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_PROP,
>-		     signal | sink_fmt->yuv_seq | input_sel |
>+		     acq_prop | sink_fmt->yuv_seq |
> 		     RKISP1_CIF_ISP_ACQ_PROP_BAYER_PAT(sink_fmt->bayer_pat) |
> 		     RKISP1_CIF_ISP_ACQ_PROP_FIELD_SEL_ALL);
> 	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ACQ_NR_FRAMES, 0);
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 33/55] media: rkisp1: isp: Initialize some variables at declaration time
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  5:04     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:04 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Intialize the src_fmt and sink_fmt variable when declaring them in
>rkisp1_config_isp().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 ++---
> 1 file changed, 2 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 4496af991c82..bf44f10200f5 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -142,12 +142,11 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
>-	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
>+	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>
>-	sink_fmt = isp->sink_fmt;
>-	src_fmt = isp->src_fmt;
> 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
> 					  V4L2_SUBDEV_FORMAT_ACTIVE);
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 33/55] media: rkisp1: isp: Initialize some variables at declaration time
@ 2022-06-25  5:04     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:04 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Intialize the src_fmt and sink_fmt variable when declaring them in
>rkisp1_config_isp().
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 5 ++---
> 1 file changed, 2 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 4496af991c82..bf44f10200f5 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -142,12 +142,11 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> {
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
>-	const struct rkisp1_mbus_info *src_fmt, *sink_fmt;
>+	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
>+	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
> 	struct v4l2_mbus_framefmt *sink_frm;
> 	struct v4l2_rect *sink_crop;
>
>-	sink_fmt = isp->sink_fmt;
>-	src_fmt = isp->src_fmt;
> 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
> 					  V4L2_SUBDEV_FORMAT_ACTIVE);
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 34/55] media: rkisp1: isp: Fix whitespace issues
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  5:05     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:05 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Add missing blank lines after variable declaration blocks, and fix
>indentation issues.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 8 +++++---
> 1 file changed, 5 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index bf44f10200f5..86d496855374 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -79,7 +79,8 @@ rkisp1_isp_get_pad_fmt(struct rkisp1_isp *isp,
> {
> 	struct v4l2_subdev_state state = {
> 		.pads = isp->pad_cfg
>-		};
>+	};
>+
> 	if (which == V4L2_SUBDEV_FORMAT_TRY)
> 		return v4l2_subdev_get_try_format(&isp->sd, sd_state, pad);
> 	else
>@@ -93,7 +94,8 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
> {
> 	struct v4l2_subdev_state state = {
> 		.pads = isp->pad_cfg
>-		};
>+	};
>+
> 	if (which == V4L2_SUBDEV_FORMAT_TRY)
> 		return v4l2_subdev_get_try_crop(&isp->sd, sd_state, pad);
> 	else
>@@ -893,8 +895,8 @@ static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
> 	struct v4l2_event event = {
> 		.type = V4L2_EVENT_FRAME_SYNC,
> 	};
>-	event.u.frame_sync.frame_sequence = isp->frame_sequence;
>
>+	event.u.frame_sync.frame_sequence = isp->frame_sequence;
> 	v4l2_event_queue(isp->sd.devnode, &event);
> }
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 34/55] media: rkisp1: isp: Fix whitespace issues
@ 2022-06-25  5:05     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:05 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Add missing blank lines after variable declaration blocks, and fix
>indentation issues.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 8 +++++---
> 1 file changed, 5 insertions(+), 3 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index bf44f10200f5..86d496855374 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -79,7 +79,8 @@ rkisp1_isp_get_pad_fmt(struct rkisp1_isp *isp,
> {
> 	struct v4l2_subdev_state state = {
> 		.pads = isp->pad_cfg
>-		};
>+	};
>+
> 	if (which == V4L2_SUBDEV_FORMAT_TRY)
> 		return v4l2_subdev_get_try_format(&isp->sd, sd_state, pad);
> 	else
>@@ -93,7 +94,8 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
> {
> 	struct v4l2_subdev_state state = {
> 		.pads = isp->pad_cfg
>-		};
>+	};
>+
> 	if (which == V4L2_SUBDEV_FORMAT_TRY)
> 		return v4l2_subdev_get_try_crop(&isp->sd, sd_state, pad);
> 	else
>@@ -893,8 +895,8 @@ static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
> 	struct v4l2_event event = {
> 		.type = V4L2_EVENT_FRAME_SYNC,
> 	};
>-	event.u.frame_sync.frame_sequence = isp->frame_sequence;
>
>+	event.u.frame_sync.frame_sequence = isp->frame_sequence;
> 	v4l2_event_queue(isp->sd.devnode, &event);
> }
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 35/55] media: rkisp1: isp: Constify various local variables
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  5:07     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:07 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>A set of local variables point to structure that are not meant to be
>modified. Constify them.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 10 +++++-----
> 1 file changed, 5 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 86d496855374..91b37f2dca91 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -113,7 +113,7 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
>  */
> static void rkisp1_config_ism(struct rkisp1_isp *isp)
> {
>-	struct v4l2_rect *src_crop =
>+	const struct v4l2_rect *src_crop =
> 		rkisp1_isp_get_pad_crop(isp, NULL,
> 					RKISP1_ISP_PAD_SOURCE_VIDEO,
> 					V4L2_SUBDEV_FORMAT_ACTIVE);
>@@ -146,8 +146,8 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
> 	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
> 	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
>-	struct v4l2_mbus_framefmt *sink_frm;
>-	struct v4l2_rect *sink_crop;
>+	const struct v4l2_mbus_framefmt *sink_frm;
>+	const struct v4l2_rect *sink_crop;
>
> 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
>@@ -557,7 +557,7 @@ static void rkisp1_isp_set_sink_crop(struct rkisp1_isp *isp,
> 				     struct v4l2_rect *r, unsigned int which)
> {
> 	struct v4l2_rect *sink_crop, *src_crop;
>-	struct v4l2_mbus_framefmt *sink_fmt;
>+	const struct v4l2_mbus_framefmt *sink_fmt;
>
> 	sink_crop = rkisp1_isp_get_pad_crop(isp, sd_state,
> 					    RKISP1_ISP_PAD_SINK_VIDEO,
>@@ -742,7 +742,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	struct rkisp1_sensor_async *asd;
>+	const struct rkisp1_sensor_async *asd;
> 	int ret;
>
> 	if (!enable) {
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 35/55] media: rkisp1: isp: Constify various local variables
@ 2022-06-25  5:07     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:07 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>A set of local variables point to structure that are not meant to be
>modified. Constify them.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 10 +++++-----
> 1 file changed, 5 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 86d496855374..91b37f2dca91 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -113,7 +113,7 @@ rkisp1_isp_get_pad_crop(struct rkisp1_isp *isp,
>  */
> static void rkisp1_config_ism(struct rkisp1_isp *isp)
> {
>-	struct v4l2_rect *src_crop =
>+	const struct v4l2_rect *src_crop =
> 		rkisp1_isp_get_pad_crop(isp, NULL,
> 					RKISP1_ISP_PAD_SOURCE_VIDEO,
> 					V4L2_SUBDEV_FORMAT_ACTIVE);
>@@ -146,8 +146,8 @@ static int rkisp1_config_isp(struct rkisp1_isp *isp,
> 	u32 isp_ctrl = 0, irq_mask = 0, acq_mult = 0, acq_prop = 0;
> 	const struct rkisp1_mbus_info *sink_fmt = isp->sink_fmt;
> 	const struct rkisp1_mbus_info *src_fmt = isp->src_fmt;
>-	struct v4l2_mbus_framefmt *sink_frm;
>-	struct v4l2_rect *sink_crop;
>+	const struct v4l2_mbus_framefmt *sink_frm;
>+	const struct v4l2_rect *sink_crop;
>
> 	sink_frm = rkisp1_isp_get_pad_fmt(isp, NULL,
> 					  RKISP1_ISP_PAD_SINK_VIDEO,
>@@ -557,7 +557,7 @@ static void rkisp1_isp_set_sink_crop(struct rkisp1_isp *isp,
> 				     struct v4l2_rect *r, unsigned int which)
> {
> 	struct v4l2_rect *sink_crop, *src_crop;
>-	struct v4l2_mbus_framefmt *sink_fmt;
>+	const struct v4l2_mbus_framefmt *sink_fmt;
>
> 	sink_crop = rkisp1_isp_get_pad_crop(isp, sd_state,
> 					    RKISP1_ISP_PAD_SINK_VIDEO,
>@@ -742,7 +742,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	struct rkisp1_sensor_async *asd;
>+	const struct rkisp1_sensor_async *asd;
> 	int ret;
>
> 	if (!enable) {
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 36/55] media: rkisp1: isp: Rename rkisp1_get_remote_source()
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  5:09     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:09 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Rename the rkisp1_get_remote_source() function to
>rkisp1_isp_get_source() to use a consistent rkisp1_isp_* prefix for all
>ISP functions, and drop the "remote" as the source can't be local.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 91b37f2dca91..627b1ad3bf26 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -58,7 +58,7 @@
>  * Helpers
>  */
>
>-static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
>+static struct v4l2_subdev *rkisp1_isp_get_source(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
> 	struct media_entity *sensor_me;
>@@ -754,7 +754,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return 0;
> 	}
>
>-	rkisp1->source = rkisp1_get_remote_source(sd);
>+	rkisp1->source = rkisp1_isp_get_source(sd);
> 	if (!rkisp1->source) {
> 		dev_warn(rkisp1->dev, "No link between isp and source\n");
> 		return -ENODEV;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 36/55] media: rkisp1: isp: Rename rkisp1_get_remote_source()
@ 2022-06-25  5:09     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  5:09 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Rename the rkisp1_get_remote_source() function to
>rkisp1_isp_get_source() to use a consistent rkisp1_isp_* prefix for all
>ISP functions, and drop the "remote" as the source can't be local.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by Dafna Hirschfeld <dafna@fastmail.com>

>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 91b37f2dca91..627b1ad3bf26 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -58,7 +58,7 @@
>  * Helpers
>  */
>
>-static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
>+static struct v4l2_subdev *rkisp1_isp_get_source(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
> 	struct media_entity *sensor_me;
>@@ -754,7 +754,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return 0;
> 	}
>
>-	rkisp1->source = rkisp1_get_remote_source(sd);
>+	rkisp1->source = rkisp1_isp_get_source(sd);
> 	if (!rkisp1->source) {
> 		dev_warn(rkisp1->dev, "No link between isp and source\n");
> 		return -ENODEV;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  7:00     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  7:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The CSI receiver is a component separate from the ISP or the resizers.
>It is actually optional, not all device model include a CSI receiver. On
>some SoCs CSI-2 support can be provided through an external CSI-2
>receiver, connected to the ISP's parallel input.
>
>To support those use cases, create a V4L2 subdev to model the CSI
>receiver. It will allow the driver to handle both internal and external
>CSI receivers the same way.
>
>The next commit will plumb the CSI subdev to the rest of the driver,
>replacing direct function calls.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
> 4 files changed, 313 insertions(+)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 3c55e922346e..0ab49d1feb55 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
> 	RKISP1_RSZ_PAD_MAX
> };
>
>+/* enum for the csi receiver pads */
>+enum rkisp1_csi_pad {
>+	RKISP1_CSI_PAD_SINK,
>+	RKISP1_CSI_PAD_SRC,
>+	RKISP1_CSI_PAD_MAX

I'd call it RKISP1_CSI_PAD_NUM

>+};
>+
> /* enum for the capture id */
> enum rkisp1_stream_id {
> 	RKISP1_MAINPATH,
>@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
>  * @rkisp1: pointer to the rkisp1 device
>  * @dphy: a pointer to the phy
>  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
>+ * @sd: v4l2_subdev variable
>+ * @pads: media pads
>+ * @pad_cfg: configurations for the pads
>+ * @ops_lock: a lock for the subdev ops
>+ * @source: source in-use, set when starting streaming
>  */
> struct rkisp1_csi {
> 	struct rkisp1_device *rkisp1;
> 	struct phy *dphy;
> 	bool is_dphy_errctrl_disabled;
>+	struct v4l2_subdev sd;
>+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
>+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
>+	struct mutex ops_lock; /* serialize the subdevice ops */
>+	struct rkisp1_sensor_async *source;
> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 425a3b014089..8182694a6fe0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -15,10 +15,34 @@
> #include <linux/phy/phy-mipi-dphy.h>
>
> #include <media/v4l2-ctrls.h>
>+#include <media/v4l2-fwnode.h>
>
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
>+
>+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
>+
>+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
>+{
>+	return container_of(sd, struct rkisp1_csi, sd);
>+}
>+
>+static struct v4l2_mbus_framefmt *
>+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
>+		       struct v4l2_subdev_state *sd_state,
>+		       unsigned int pad, u32 which)
>+{
>+	struct v4l2_subdev_state state = {
>+		.pads = csi->pad_cfg
>+	};

newline here
>+	if (which == V4L2_SUBDEV_FORMAT_TRY)
>+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
>+	else
>+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
>+}
>+
> static int rkisp1_csi_config(struct rkisp1_csi *csi,
> 			     const struct rkisp1_sensor_async *sensor)
> {
>@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
> 	return IRQ_HANDLED;
> }
>
>+/* ----------------------------------------------------------------------------
>+ * Subdev pad operations
>+ */
>+
>+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
>+				   struct v4l2_subdev_state *sd_state,
>+				   struct v4l2_mbus_framefmt *format,
>+				   unsigned int which)
>+{
>+	struct v4l2_mbus_framefmt *sink_fmt;
>+
>+	/* We don't set the src format directly; take it from the sink format */
>+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>+					  which);
>+
>+	*format = *sink_fmt;
>+}
>+
>+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
>+				    struct v4l2_subdev_state *sd_state,
>+				    struct v4l2_mbus_framefmt *format,
>+				    unsigned int which)
>+{
>+	const struct rkisp1_mbus_info *mbus_info;
>+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>+
>+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>+					  which);
>+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
>+					 which);
>+
>+	sink_fmt->code = format->code;
>+
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
>+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
>+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>+	}
>+
>+	sink_fmt->width = clamp_t(u32, format->width,
>+				  RKISP1_ISP_MIN_WIDTH,
>+				  RKISP1_ISP_MAX_WIDTH);
>+	sink_fmt->height = clamp_t(u32, format->height,
>+				   RKISP1_ISP_MIN_HEIGHT,
>+				   RKISP1_ISP_MAX_HEIGHT);
>+
>+	/* Propagate to source pad */
>+	src_fmt->code = sink_fmt->code;
>+	src_fmt->width = sink_fmt->width;
>+	src_fmt->height = sink_fmt->height;
>+

why here you don't do '*src_fmt = *sink_fmt' instead of per field propaget ?

>+	*format = *sink_fmt;
>+}
>+
>+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
>+				     struct v4l2_subdev_state *sd_state,
>+				     struct v4l2_subdev_mbus_code_enum *code)
>+{
>+	unsigned int i;
>+	int pos = 0;
>+
>+	if (code->index >= rkisp1_mbus_info_length())
>+		return -EINVAL;
>+
>+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
>+		const struct rkisp1_mbus_info *fmt =
>+			rkisp1_mbus_info_get_by_index(i);
>+
>+		if (fmt->direction & RKISP1_ISP_SD_SINK)
>+			pos++;
>+
>+		if (code->index == pos - 1) {
>+			code->code = fmt->mbus_code;
>+			return 0;
>+		}
>+	}
>+
>+	return -EINVAL;
>+}
>+
>+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
>+				  struct v4l2_subdev_state *sd_state)
>+{
>+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>+
>+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>+					      RKISP1_CSI_PAD_SRC);

last argument here should be RKISP1_CSI_PAD_SINK ?

>+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
>+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
>+	sink_fmt->field = V4L2_FIELD_NONE;
>+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
>+
>+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>+					     RKISP1_CSI_PAD_SINK);

last argument here should be RKISP1_CSI_PAD_SRC ?

>+	*src_fmt = *sink_fmt;
>+
>+	return 0;
>+}
>+
>+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
>+			      struct v4l2_subdev_state *sd_state,
>+			      struct v4l2_subdev_format *fmt)
>+{
>+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>+
>+	mutex_lock(&csi->ops_lock);
>+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
>+					      fmt->which);
>+	mutex_unlock(&csi->ops_lock);
>+	return 0;
>+}
>+
>+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
>+			      struct v4l2_subdev_state *sd_state,
>+			      struct v4l2_subdev_format *fmt)
>+{
>+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>+
>+	mutex_lock(&csi->ops_lock);
>+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
>+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
>+					fmt->which);
>+	else
>+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
>+				       fmt->which);
>+
>+	mutex_unlock(&csi->ops_lock);
>+	return 0;
>+}
>+
>+/* ----------------------------------------------------------------------------
>+ * Subdev video operations
>+ */
>+
>+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
>+{
>+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	struct media_pad *source_pad;
>+	struct v4l2_subdev *source;
>+	int ret;
>+
>+	if (!enable) {
>+		v4l2_subdev_call(csi->source->sd, video, s_stream,
>+				 false);
>+
>+		rkisp1_csi_stop(csi);
>+
>+		return ret;

ret is uninitialized here

>+	}
>+
>+	source_pad = media_entity_remote_source_pad(&sd->entity);
>+	if (IS_ERR(source_pad)) {
>+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);

here you should print 'ERR_PTR(source_pad)' instead of 'ret'

thanks,
Dafna

>+		return -EPIPE;
>+	}
>+
>+	source = media_entity_to_v4l2_subdev(source_pad->entity);
>+	if (!source) {
>+		/* This should really not happen, so is not worth a message. */
>+		return -EPIPE;
>+	}
>+
>+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
>+				   asd);
>+
>+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
>+		return -EINVAL;
>+
>+	mutex_lock(&csi->ops_lock);
>+	ret = rkisp1_csi_start(csi, csi->source);
>+	mutex_unlock(&csi->ops_lock);
>+	if (ret)
>+		return ret;
>+
>+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
>+
>+	return 0;
>+}
>+
>+/* ----------------------------------------------------------------------------
>+ * Registration
>+ */
>+
>+static const struct media_entity_operations rkisp1_csi_media_ops = {
>+	.link_validate = v4l2_subdev_link_validate,
>+};
>+
>+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
>+	.s_stream = rkisp1_csi_s_stream,
>+};
>+
>+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
>+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
>+	.init_cfg = rkisp1_csi_init_config,
>+	.get_fmt = rkisp1_csi_get_fmt,
>+	.set_fmt = rkisp1_csi_set_fmt,
>+};
>+
>+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
>+	.video = &rkisp1_csi_video_ops,
>+	.pad = &rkisp1_csi_pad_ops,
>+};
>+
>+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+	struct v4l2_subdev_state state = {};
>+	struct media_pad *pads;
>+	struct v4l2_subdev *sd;
>+	int ret;
>+
>+	csi->rkisp1 = rkisp1;
>+	mutex_init(&csi->ops_lock);
>+
>+	sd = &csi->sd;
>+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
>+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
>+	sd->entity.ops = &rkisp1_csi_media_ops;
>+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
>+	sd->owner = THIS_MODULE;
>+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
>+
>+	pads = csi->pads;
>+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
>+					  MEDIA_PAD_FL_MUST_CONNECT;
>+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
>+					 MEDIA_PAD_FL_MUST_CONNECT;
>+
>+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
>+	if (ret)
>+		goto error;
>+
>+	state.pads = csi->pad_cfg;
>+	rkisp1_csi_init_config(sd, &state);
>+
>+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
>+	if (ret) {
>+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
>+		goto error;
>+	}
>+
>+	return 0;
>+
>+error:
>+	media_entity_cleanup(&sd->entity);
>+	mutex_destroy(&csi->ops_lock);
>+	csi->rkisp1 = NULL;
>+	return ret;
>+}
>+
>+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+
>+	if (!csi->rkisp1)
>+		return;
>+
>+	v4l2_device_unregister_subdev(&csi->sd);
>+	media_entity_cleanup(&csi->sd.entity);
>+	mutex_destroy(&csi->ops_lock);
>+}
>+
> int rkisp1_csi_init(struct rkisp1_device *rkisp1)
> {
> 	struct rkisp1_csi *csi = &rkisp1->csi;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index 97ce7e7959ab..ddf8e5e08f55 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -13,10 +13,14 @@
>
> struct rkisp1_device;
> struct rkisp1_sensor_async;
>+struct v4l2_subdev;
>
> int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
>+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
>+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>+
> int rkisp1_csi_start(struct rkisp1_csi *csi,
> 		     const struct rkisp1_sensor_async *sensor);
> void rkisp1_csi_stop(struct rkisp1_csi *csi);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 253220188abd..faf2cd4c8149 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>
> static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
> {
>+	rkisp1_csi_unregister(rkisp1);
> 	rkisp1_params_unregister(rkisp1);
> 	rkisp1_stats_unregister(rkisp1);
> 	rkisp1_capture_devs_unregister(rkisp1);
>@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>+	ret = rkisp1_csi_register(rkisp1);
>+	if (ret)
>+		goto error;
>+
> 	ret = rkisp1_create_links(rkisp1);
> 	if (ret)
> 		goto error;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
@ 2022-06-25  7:00     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  7:00 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The CSI receiver is a component separate from the ISP or the resizers.
>It is actually optional, not all device model include a CSI receiver. On
>some SoCs CSI-2 support can be provided through an external CSI-2
>receiver, connected to the ISP's parallel input.
>
>To support those use cases, create a V4L2 subdev to model the CSI
>receiver. It will allow the driver to handle both internal and external
>CSI receivers the same way.
>
>The next commit will plumb the CSI subdev to the rest of the driver,
>replacing direct function calls.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
> 4 files changed, 313 insertions(+)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 3c55e922346e..0ab49d1feb55 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
> 	RKISP1_RSZ_PAD_MAX
> };
>
>+/* enum for the csi receiver pads */
>+enum rkisp1_csi_pad {
>+	RKISP1_CSI_PAD_SINK,
>+	RKISP1_CSI_PAD_SRC,
>+	RKISP1_CSI_PAD_MAX

I'd call it RKISP1_CSI_PAD_NUM

>+};
>+
> /* enum for the capture id */
> enum rkisp1_stream_id {
> 	RKISP1_MAINPATH,
>@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
>  * @rkisp1: pointer to the rkisp1 device
>  * @dphy: a pointer to the phy
>  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
>+ * @sd: v4l2_subdev variable
>+ * @pads: media pads
>+ * @pad_cfg: configurations for the pads
>+ * @ops_lock: a lock for the subdev ops
>+ * @source: source in-use, set when starting streaming
>  */
> struct rkisp1_csi {
> 	struct rkisp1_device *rkisp1;
> 	struct phy *dphy;
> 	bool is_dphy_errctrl_disabled;
>+	struct v4l2_subdev sd;
>+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
>+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
>+	struct mutex ops_lock; /* serialize the subdevice ops */
>+	struct rkisp1_sensor_async *source;
> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 425a3b014089..8182694a6fe0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -15,10 +15,34 @@
> #include <linux/phy/phy-mipi-dphy.h>
>
> #include <media/v4l2-ctrls.h>
>+#include <media/v4l2-fwnode.h>
>
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>
>+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
>+
>+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
>+
>+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
>+{
>+	return container_of(sd, struct rkisp1_csi, sd);
>+}
>+
>+static struct v4l2_mbus_framefmt *
>+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
>+		       struct v4l2_subdev_state *sd_state,
>+		       unsigned int pad, u32 which)
>+{
>+	struct v4l2_subdev_state state = {
>+		.pads = csi->pad_cfg
>+	};

newline here
>+	if (which == V4L2_SUBDEV_FORMAT_TRY)
>+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
>+	else
>+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
>+}
>+
> static int rkisp1_csi_config(struct rkisp1_csi *csi,
> 			     const struct rkisp1_sensor_async *sensor)
> {
>@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
> 	return IRQ_HANDLED;
> }
>
>+/* ----------------------------------------------------------------------------
>+ * Subdev pad operations
>+ */
>+
>+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
>+				   struct v4l2_subdev_state *sd_state,
>+				   struct v4l2_mbus_framefmt *format,
>+				   unsigned int which)
>+{
>+	struct v4l2_mbus_framefmt *sink_fmt;
>+
>+	/* We don't set the src format directly; take it from the sink format */
>+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>+					  which);
>+
>+	*format = *sink_fmt;
>+}
>+
>+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
>+				    struct v4l2_subdev_state *sd_state,
>+				    struct v4l2_mbus_framefmt *format,
>+				    unsigned int which)
>+{
>+	const struct rkisp1_mbus_info *mbus_info;
>+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>+
>+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>+					  which);
>+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
>+					 which);
>+
>+	sink_fmt->code = format->code;
>+
>+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
>+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
>+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>+	}
>+
>+	sink_fmt->width = clamp_t(u32, format->width,
>+				  RKISP1_ISP_MIN_WIDTH,
>+				  RKISP1_ISP_MAX_WIDTH);
>+	sink_fmt->height = clamp_t(u32, format->height,
>+				   RKISP1_ISP_MIN_HEIGHT,
>+				   RKISP1_ISP_MAX_HEIGHT);
>+
>+	/* Propagate to source pad */
>+	src_fmt->code = sink_fmt->code;
>+	src_fmt->width = sink_fmt->width;
>+	src_fmt->height = sink_fmt->height;
>+

why here you don't do '*src_fmt = *sink_fmt' instead of per field propaget ?

>+	*format = *sink_fmt;
>+}
>+
>+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
>+				     struct v4l2_subdev_state *sd_state,
>+				     struct v4l2_subdev_mbus_code_enum *code)
>+{
>+	unsigned int i;
>+	int pos = 0;
>+
>+	if (code->index >= rkisp1_mbus_info_length())
>+		return -EINVAL;
>+
>+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
>+		const struct rkisp1_mbus_info *fmt =
>+			rkisp1_mbus_info_get_by_index(i);
>+
>+		if (fmt->direction & RKISP1_ISP_SD_SINK)
>+			pos++;
>+
>+		if (code->index == pos - 1) {
>+			code->code = fmt->mbus_code;
>+			return 0;
>+		}
>+	}
>+
>+	return -EINVAL;
>+}
>+
>+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
>+				  struct v4l2_subdev_state *sd_state)
>+{
>+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>+
>+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>+					      RKISP1_CSI_PAD_SRC);

last argument here should be RKISP1_CSI_PAD_SINK ?

>+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
>+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
>+	sink_fmt->field = V4L2_FIELD_NONE;
>+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
>+
>+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>+					     RKISP1_CSI_PAD_SINK);

last argument here should be RKISP1_CSI_PAD_SRC ?

>+	*src_fmt = *sink_fmt;
>+
>+	return 0;
>+}
>+
>+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
>+			      struct v4l2_subdev_state *sd_state,
>+			      struct v4l2_subdev_format *fmt)
>+{
>+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>+
>+	mutex_lock(&csi->ops_lock);
>+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
>+					      fmt->which);
>+	mutex_unlock(&csi->ops_lock);
>+	return 0;
>+}
>+
>+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
>+			      struct v4l2_subdev_state *sd_state,
>+			      struct v4l2_subdev_format *fmt)
>+{
>+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>+
>+	mutex_lock(&csi->ops_lock);
>+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
>+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
>+					fmt->which);
>+	else
>+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
>+				       fmt->which);
>+
>+	mutex_unlock(&csi->ops_lock);
>+	return 0;
>+}
>+
>+/* ----------------------------------------------------------------------------
>+ * Subdev video operations
>+ */
>+
>+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
>+{
>+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>+	struct media_pad *source_pad;
>+	struct v4l2_subdev *source;
>+	int ret;
>+
>+	if (!enable) {
>+		v4l2_subdev_call(csi->source->sd, video, s_stream,
>+				 false);
>+
>+		rkisp1_csi_stop(csi);
>+
>+		return ret;

ret is uninitialized here

>+	}
>+
>+	source_pad = media_entity_remote_source_pad(&sd->entity);
>+	if (IS_ERR(source_pad)) {
>+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);

here you should print 'ERR_PTR(source_pad)' instead of 'ret'

thanks,
Dafna

>+		return -EPIPE;
>+	}
>+
>+	source = media_entity_to_v4l2_subdev(source_pad->entity);
>+	if (!source) {
>+		/* This should really not happen, so is not worth a message. */
>+		return -EPIPE;
>+	}
>+
>+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
>+				   asd);
>+
>+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
>+		return -EINVAL;
>+
>+	mutex_lock(&csi->ops_lock);
>+	ret = rkisp1_csi_start(csi, csi->source);
>+	mutex_unlock(&csi->ops_lock);
>+	if (ret)
>+		return ret;
>+
>+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
>+
>+	return 0;
>+}
>+
>+/* ----------------------------------------------------------------------------
>+ * Registration
>+ */
>+
>+static const struct media_entity_operations rkisp1_csi_media_ops = {
>+	.link_validate = v4l2_subdev_link_validate,
>+};
>+
>+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
>+	.s_stream = rkisp1_csi_s_stream,
>+};
>+
>+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
>+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
>+	.init_cfg = rkisp1_csi_init_config,
>+	.get_fmt = rkisp1_csi_get_fmt,
>+	.set_fmt = rkisp1_csi_set_fmt,
>+};
>+
>+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
>+	.video = &rkisp1_csi_video_ops,
>+	.pad = &rkisp1_csi_pad_ops,
>+};
>+
>+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+	struct v4l2_subdev_state state = {};
>+	struct media_pad *pads;
>+	struct v4l2_subdev *sd;
>+	int ret;
>+
>+	csi->rkisp1 = rkisp1;
>+	mutex_init(&csi->ops_lock);
>+
>+	sd = &csi->sd;
>+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
>+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
>+	sd->entity.ops = &rkisp1_csi_media_ops;
>+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
>+	sd->owner = THIS_MODULE;
>+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
>+
>+	pads = csi->pads;
>+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
>+					  MEDIA_PAD_FL_MUST_CONNECT;
>+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
>+					 MEDIA_PAD_FL_MUST_CONNECT;
>+
>+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
>+	if (ret)
>+		goto error;
>+
>+	state.pads = csi->pad_cfg;
>+	rkisp1_csi_init_config(sd, &state);
>+
>+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
>+	if (ret) {
>+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
>+		goto error;
>+	}
>+
>+	return 0;
>+
>+error:
>+	media_entity_cleanup(&sd->entity);
>+	mutex_destroy(&csi->ops_lock);
>+	csi->rkisp1 = NULL;
>+	return ret;
>+}
>+
>+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+
>+	if (!csi->rkisp1)
>+		return;
>+
>+	v4l2_device_unregister_subdev(&csi->sd);
>+	media_entity_cleanup(&csi->sd.entity);
>+	mutex_destroy(&csi->ops_lock);
>+}
>+
> int rkisp1_csi_init(struct rkisp1_device *rkisp1)
> {
> 	struct rkisp1_csi *csi = &rkisp1->csi;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index 97ce7e7959ab..ddf8e5e08f55 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -13,10 +13,14 @@
>
> struct rkisp1_device;
> struct rkisp1_sensor_async;
>+struct v4l2_subdev;
>
> int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>
>+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
>+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>+
> int rkisp1_csi_start(struct rkisp1_csi *csi,
> 		     const struct rkisp1_sensor_async *sensor);
> void rkisp1_csi_stop(struct rkisp1_csi *csi);
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 253220188abd..faf2cd4c8149 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>
> static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
> {
>+	rkisp1_csi_unregister(rkisp1);
> 	rkisp1_params_unregister(rkisp1);
> 	rkisp1_stats_unregister(rkisp1);
> 	rkisp1_capture_devs_unregister(rkisp1);
>@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>+	ret = rkisp1_csi_register(rkisp1);
>+	if (ret)
>+		goto error;
>+
> 	ret = rkisp1_create_links(rkisp1);
> 	if (ret)
> 		goto error;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-25  7:45     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  7:45 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Connect the CSI receiver subdevice into the rest of the driver. This
>includes:

To make it clear where you put the csi, i'll add here
'Connect the CSI subdevice between the source
and the isp' or something like that.

Also the sketch 'Media Topology' in rkisp1-dev.c should be updated.
I'd also wonder if we should ignore src configuration of the isp entity
since it must be identical to the sink of the csi.

>- calling the subdevice via the v4l2 subdev API
>- moving the async notifier for the sensor from the ISP to the CSI
>  receiver
>- in the ISP, create a media link to the CSI receiver, and remove the
>  media link creation to the sensor
>- in the CSI receiver, create a media link to the sensor
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
> 4 files changed, 53 insertions(+), 44 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 8182694a6fe0..96712b467dde 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
> 		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
> }
>
>+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
>+			   struct rkisp1_sensor_async *s_asd,
>+			   unsigned int source_pad)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+	int ret;		

extra space after 'ret;' ?

>+
>+	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
>+						V4L2_CID_PIXEL_RATE);
>+	if (!s_asd->pixel_rate_ctrl) {
>+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
>+			sd->name);
>+		return -EINVAL;
>+	}
>+
>+	/* Create the link from the sensor to the CSI receiver. */
>+	ret = media_create_pad_link(&sd->entity, source_pad,
>+				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
>+				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
>+	if (ret) {
>+		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
>+			sd->name);
>+		return ret;
>+	}
>+
>+	return 0;
>+}
>+
> static int rkisp1_csi_config(struct rkisp1_csi *csi,
> 			     const struct rkisp1_sensor_async *sensor)
> {
>@@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> }
>
>-int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     const struct rkisp1_sensor_async *sensor)
>+static int rkisp1_csi_start(struct rkisp1_csi *csi,
>+			    const struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	union phy_configure_opts opts;
>@@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
> 	return 0;
> }
>
>-void rkisp1_csi_stop(struct rkisp1_csi *csi)
>+static void rkisp1_csi_stop(struct rkisp1_csi *csi)
> {
> 	rkisp1_csi_disable(csi);
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index ddf8e5e08f55..eadcd24f65fb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> int rkisp1_csi_register(struct rkisp1_device *rkisp1);
> void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>
>-int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     const struct rkisp1_sensor_async *sensor);
>-void rkisp1_csi_stop(struct rkisp1_csi *csi);
>+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
>+			   struct rkisp1_sensor_async *s_asd,
>+			   unsigned int source_pad);
>
> #endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index faf2cd4c8149..a3e182c86bdd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -17,6 +17,7 @@
> #include <linux/pinctrl/consumer.h>
> #include <linux/pm_runtime.h>
> #include <media/v4l2-fwnode.h>
>+#include <media/v4l2-mc.h>
>
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>@@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 		container_of(asd, struct rkisp1_sensor_async, asd);
> 	int source_pad;
>
>-	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
>-						V4L2_CID_PIXEL_RATE);
>-	if (!s_asd->pixel_rate_ctrl) {
>-		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
>-			sd->name);
>-		return -EINVAL;
>-	}
>-
> 	s_asd->sd = sd;
>
>-	/* Create the link to the sensor. */
> 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> 						 MEDIA_PAD_FL_SOURCE);
> 	if (source_pad < 0) {
>@@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 		return source_pad;
> 	}
>
>-	return media_create_pad_link(&sd->entity, source_pad,
>-				     &rkisp1->isp.sd.entity,
>-				     RKISP1_ISP_PAD_SINK_VIDEO,
>-				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
>+	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
> }
>
> static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
>@@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> 	unsigned int i;
> 	int ret;
>
>+	/* Link the CSI receiver to the ISP. */
>+	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
>+				    &rkisp1->isp.sd.entity,
>+				    RKISP1_ISP_PAD_SINK_VIDEO,
>+				    MEDIA_LNK_FL_ENABLED);

should this also be immutable?

>+	if (ret)
>+		return ret;
>+
> 	/* create ISP->RSZ->CAP links */
> 	for (i = 0; i < 2; i++) {
> 		struct media_entity *resizer =
>@@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>-	ret = rkisp1_subdev_notifier_register(rkisp1);
>-	if (ret) {
>-		dev_err(rkisp1->dev,
>-			"Failed to register subdev notifier(%d)\n", ret);
>-		goto error;
>-	}
>-
> 	return 0;
>
> error:
>@@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	if (ret)
> 		goto err_cleanup_csi;
>
>+	ret = rkisp1_subdev_notifier_register(rkisp1);
>+	if (ret)
>+		goto err_unreg_entities;
>+
> 	rkisp1_debug_init(rkisp1);
>
> 	return 0;
>
>+err_unreg_entities:
>+	rkisp1_entities_unregister(rkisp1);
> err_cleanup_csi:
> 	rkisp1_csi_cleanup(rkisp1);
> err_unreg_media_dev:
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 5afb8be311c7..260c9ce0dca4 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -16,7 +16,6 @@
> #include <media/v4l2-event.h>
>
> #include "rkisp1-common.h"
>-#include "rkisp1-csi.h"
>
> #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
>@@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	const struct rkisp1_sensor_async *asd;
> 	struct media_pad *source_pad;
> 	int ret;
>
> 	if (!enable) {
> 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>-
>-		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(isp);
>-
> 		return 0;
> 	}
>
>@@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return -EPIPE;
> 	}
>
>-	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
>-			   asd);
>-
>-	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
>-		return -EINVAL;
>+	if (rkisp1->source != &rkisp1->csi.sd)
>+		return -EPIPE;

This is not very clear, 'source' should point to the remote source (the one outside this driver)
so why should it be 'csi.sd' ?
Or is it that now 'rkips1->source' might be either the remote source or csi? if so I think it is a bit confusing.

>
> 	isp->frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
>+	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
> 	if (ret)
> 		goto mutex_unlock;
>
> 	rkisp1_isp_start(isp);
>
>-	ret = rkisp1_csi_start(&rkisp1->csi, asd);
>-	if (ret) {
>-		rkisp1_isp_stop(isp);
>-		goto mutex_unlock;
>-	}
>-
> 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);

Now that isp should call 's_stream' for 'rkisp1->csi->sd' and not 'rkisp1->source'.

thanks,
Dafna

> 	if (ret) {
> 		rkisp1_isp_stop(isp);
>-		rkisp1_csi_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
@ 2022-06-25  7:45     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-25  7:45 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>Connect the CSI receiver subdevice into the rest of the driver. This
>includes:

To make it clear where you put the csi, i'll add here
'Connect the CSI subdevice between the source
and the isp' or something like that.

Also the sketch 'Media Topology' in rkisp1-dev.c should be updated.
I'd also wonder if we should ignore src configuration of the isp entity
since it must be identical to the sink of the csi.

>- calling the subdevice via the v4l2 subdev API
>- moving the async notifier for the sensor from the ISP to the CSI
>  receiver
>- in the ISP, create a media link to the CSI receiver, and remove the
>  media link creation to the sensor
>- in the CSI receiver, create a media link to the sensor
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
> .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
> 4 files changed, 53 insertions(+), 44 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>index 8182694a6fe0..96712b467dde 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>@@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
> 		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
> }
>
>+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
>+			   struct rkisp1_sensor_async *s_asd,
>+			   unsigned int source_pad)
>+{
>+	struct rkisp1_csi *csi = &rkisp1->csi;
>+	int ret;		

extra space after 'ret;' ?

>+
>+	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
>+						V4L2_CID_PIXEL_RATE);
>+	if (!s_asd->pixel_rate_ctrl) {
>+		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
>+			sd->name);
>+		return -EINVAL;
>+	}
>+
>+	/* Create the link from the sensor to the CSI receiver. */
>+	ret = media_create_pad_link(&sd->entity, source_pad,
>+				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
>+				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
>+	if (ret) {
>+		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
>+			sd->name);
>+		return ret;
>+	}
>+
>+	return 0;
>+}
>+
> static int rkisp1_csi_config(struct rkisp1_csi *csi,
> 			     const struct rkisp1_sensor_async *sensor)
> {
>@@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> 		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> }
>
>-int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     const struct rkisp1_sensor_async *sensor)
>+static int rkisp1_csi_start(struct rkisp1_csi *csi,
>+			    const struct rkisp1_sensor_async *sensor)
> {
> 	struct rkisp1_device *rkisp1 = csi->rkisp1;
> 	union phy_configure_opts opts;
>@@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
> 	return 0;
> }
>
>-void rkisp1_csi_stop(struct rkisp1_csi *csi)
>+static void rkisp1_csi_stop(struct rkisp1_csi *csi)
> {
> 	rkisp1_csi_disable(csi);
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>index ddf8e5e08f55..eadcd24f65fb 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>@@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> int rkisp1_csi_register(struct rkisp1_device *rkisp1);
> void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>
>-int rkisp1_csi_start(struct rkisp1_csi *csi,
>-		     const struct rkisp1_sensor_async *sensor);
>-void rkisp1_csi_stop(struct rkisp1_csi *csi);
>+int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
>+			   struct rkisp1_sensor_async *s_asd,
>+			   unsigned int source_pad);
>
> #endif /* _RKISP1_CSI_H */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index faf2cd4c8149..a3e182c86bdd 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -17,6 +17,7 @@
> #include <linux/pinctrl/consumer.h>
> #include <linux/pm_runtime.h>
> #include <media/v4l2-fwnode.h>
>+#include <media/v4l2-mc.h>
>
> #include "rkisp1-common.h"
> #include "rkisp1-csi.h"
>@@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 		container_of(asd, struct rkisp1_sensor_async, asd);
> 	int source_pad;
>
>-	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
>-						V4L2_CID_PIXEL_RATE);
>-	if (!s_asd->pixel_rate_ctrl) {
>-		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
>-			sd->name);
>-		return -EINVAL;
>-	}
>-
> 	s_asd->sd = sd;
>
>-	/* Create the link to the sensor. */
> 	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> 						 MEDIA_PAD_FL_SOURCE);
> 	if (source_pad < 0) {
>@@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 		return source_pad;
> 	}
>
>-	return media_create_pad_link(&sd->entity, source_pad,
>-				     &rkisp1->isp.sd.entity,
>-				     RKISP1_ISP_PAD_SINK_VIDEO,
>-				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
>+	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
> }
>
> static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
>@@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> 	unsigned int i;
> 	int ret;
>
>+	/* Link the CSI receiver to the ISP. */
>+	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
>+				    &rkisp1->isp.sd.entity,
>+				    RKISP1_ISP_PAD_SINK_VIDEO,
>+				    MEDIA_LNK_FL_ENABLED);

should this also be immutable?

>+	if (ret)
>+		return ret;
>+
> 	/* create ISP->RSZ->CAP links */
> 	for (i = 0; i < 2; i++) {
> 		struct media_entity *resizer =
>@@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> 	if (ret)
> 		goto error;
>
>-	ret = rkisp1_subdev_notifier_register(rkisp1);
>-	if (ret) {
>-		dev_err(rkisp1->dev,
>-			"Failed to register subdev notifier(%d)\n", ret);
>-		goto error;
>-	}
>-
> 	return 0;
>
> error:
>@@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
> 	if (ret)
> 		goto err_cleanup_csi;
>
>+	ret = rkisp1_subdev_notifier_register(rkisp1);
>+	if (ret)
>+		goto err_unreg_entities;
>+
> 	rkisp1_debug_init(rkisp1);
>
> 	return 0;
>
>+err_unreg_entities:
>+	rkisp1_entities_unregister(rkisp1);
> err_cleanup_csi:
> 	rkisp1_csi_cleanup(rkisp1);
> err_unreg_media_dev:
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index 5afb8be311c7..260c9ce0dca4 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -16,7 +16,6 @@
> #include <media/v4l2-event.h>
>
> #include "rkisp1-common.h"
>-#include "rkisp1-csi.h"
>
> #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
>@@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> {
> 	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> 	struct rkisp1_device *rkisp1 = isp->rkisp1;
>-	const struct rkisp1_sensor_async *asd;
> 	struct media_pad *source_pad;
> 	int ret;
>
> 	if (!enable) {
> 		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>-
>-		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(isp);
>-
> 		return 0;
> 	}
>
>@@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return -EPIPE;
> 	}
>
>-	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
>-			   asd);
>-
>-	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
>-		return -EINVAL;
>+	if (rkisp1->source != &rkisp1->csi.sd)
>+		return -EPIPE;

This is not very clear, 'source' should point to the remote source (the one outside this driver)
so why should it be 'csi.sd' ?
Or is it that now 'rkips1->source' might be either the remote source or csi? if so I think it is a bit confusing.

>
> 	isp->frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
>+	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
> 	if (ret)
> 		goto mutex_unlock;
>
> 	rkisp1_isp_start(isp);
>
>-	ret = rkisp1_csi_start(&rkisp1->csi, asd);
>-	if (ret) {
>-		rkisp1_isp_stop(isp);
>-		goto mutex_unlock;
>-	}
>-
> 	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);

Now that isp should call 's_stream' for 'rkisp1->csi->sd' and not 'rkisp1->source'.

thanks,
Dafna

> 	if (ret) {
> 		rkisp1_isp_stop(isp);
>-		rkisp1_csi_stop(&rkisp1->csi);
> 		goto mutex_unlock;
> 	}
>
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 18/55] media: rkisp1: Split CSI handling to separate file
  2022-06-25  3:48     ` Dafna Hirschfeld
@ 2022-06-25 10:18       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 10:18 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Sat, Jun 25, 2022 at 06:48:54AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:10, Paul Elder wrote:
> > Not all ISP instances include a MIPI CSI-2 receiver. To prepare for
> > making it optional, move code related to the CSI-2 receiver to a
> > separate file.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../media/platform/rockchip/rkisp1/Makefile   |   1 +
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 +-
> >  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 193 ++++++++++++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +++
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  32 +--
> >  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 153 +-------------
> >  6 files changed, 257 insertions(+), 167 deletions(-)
> >  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/Makefile b/drivers/media/platform/rockchip/rkisp1/Makefile
> > index f7543a82aa10..b3844c4f7623 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/Makefile
> > +++ b/drivers/media/platform/rockchip/rkisp1/Makefile
> > @@ -2,6 +2,7 @@
> > 
> >  rockchip-isp1-y := rkisp1-capture.o \
> >  		   rkisp1-common.o \
> > +		   rkisp1-csi.o \
> >  		   rkisp1-dev.o \
> >  		   rkisp1-isp.o \
> >  		   rkisp1-resizer.o \
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index 60c5462e1746..a52fa9e0dd66 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -123,7 +123,6 @@ struct rkisp1_info {
> >   * @mbus_flags:		media bus (V4L2_MBUS_*) flags
> >   * @sd:			a pointer to v4l2_subdev struct of the sensor
> >   * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
> > - * @dphy:		a pointer to the phy
> >   */
> >  struct rkisp1_sensor_async {
> >  	struct v4l2_async_subdev asd;
> > @@ -134,7 +133,19 @@ struct rkisp1_sensor_async {
> >  	unsigned int mbus_flags;
> >  	struct v4l2_subdev *sd;
> >  	struct v4l2_ctrl *pixel_rate_ctrl;
> > +};
> > +
> > +/*
> > + * struct rkisp1_csi - CSI receiver subdev
> > + *
> > + * @rkisp1: pointer to the rkisp1 device
> > + * @dphy: a pointer to the phy
> > + * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
> > + */
> > +struct rkisp1_csi {
> > +	struct rkisp1_device *rkisp1;
> 
> I think you missed initializing csi->rkips1

Indeed. It's probably fixed in a later patch as the series doesn't
crash, but I'll fix it here.

> >  	struct phy *dphy;
> > +	bool is_dphy_errctrl_disabled;
> >  };
> > 
> >  /*
> > @@ -147,7 +158,6 @@ struct rkisp1_sensor_async {
> >   * @sink_fmt:			input format
> >   * @src_fmt:			output format
> >   * @ops_lock:			ops serialization
> > - * @is_dphy_errctrl_disabled:	if dphy errctrl is disabled (avoid endless interrupt)
> >   * @frame_sequence:		used to synchronize frame_id between video devices.
> >   */
> >  struct rkisp1_isp {
> > @@ -157,7 +167,6 @@ struct rkisp1_isp {
> >  	const struct rkisp1_mbus_info *sink_fmt;
> >  	const struct rkisp1_mbus_info *src_fmt;
> >  	struct mutex ops_lock; /* serialize the subdevice ops */
> > -	bool is_dphy_errctrl_disabled;
> >  	__u32 frame_sequence;
> >  };
> > 
> > @@ -411,6 +420,7 @@ struct rkisp1_debug {
> >   * @media_dev:	   media_device variable
> >   * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
> >   * @active_sensor: sensor in-use, set when streaming on
> > + * @csi:	   internal CSI-2 receiver
> >   * @isp:	   ISP sub-device
> >   * @resizer_devs:  resizer sub-devices
> >   * @capture_devs:  capture devices
> > @@ -430,6 +440,7 @@ struct rkisp1_device {
> >  	struct media_device media_dev;
> >  	struct v4l2_async_notifier notifier;
> >  	struct rkisp1_sensor_async *active_sensor;
> > +	struct rkisp1_csi csi;
> >  	struct rkisp1_isp isp;
> >  	struct rkisp1_resizer resizer_devs[2];
> >  	struct rkisp1_capture capture_devs[2];
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > new file mode 100644
> > index 000000000000..4af04296b625
> > --- /dev/null
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > @@ -0,0 +1,193 @@
> > +// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
> > +/*
> > + * Rockchip ISP1 Driver - CSI-2 Receiver
> > + *
> > + * Copyright (C) 2019 Collabora, Ltd.
> > + * Copyright (C) 2022 Ideas on Board
> > + *
> > + * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
> > + * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
> > + */
> > +
> > +#include <linux/device.h>
> > +#include <linux/phy/phy.h>
> > +#include <linux/phy/phy-mipi-dphy.h>
> > +
> > +#include <media/v4l2-ctrls.h>
> > +
> > +#include "rkisp1-common.h"
> > +#include "rkisp1-csi.h"
> > +
> > +int rkisp1_config_mipi(struct rkisp1_csi *csi)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> > +	unsigned int lanes = rkisp1->active_sensor->lanes;
> > +	u32 mipi_ctrl;
> > +
> > +	if (lanes < 1 || lanes > 4)
> > +		return -EINVAL;
> > +
> > +	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
> > +		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
> > +		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
> > +		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
> > +
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
> > +
> > +	/* V12 could also use a newer csi2-host, but we don't want that yet */
> > +	if (rkisp1->info->isp_ver == RKISP1_V12)
> > +		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
> > +
> > +	/* Configure Data Type and Virtual Channel */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
> > +		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
> > +		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
> > +
> > +	/* Clear MIPI interrupts */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> 
> new line here

The new line was already missing, but as this patch contains more than
just a code move, I'll fix it here instead of in a separate patch.

> > +	/*
> > +	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
> > +	 * isp bus may be dead when switch isp.
> > +	 */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > +		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
> > +		     RKISP1_CIF_MIPI_ERR_DPHY |
> > +		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
> > +		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
> > +
> > +	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
> > +		"  MIPI_IMG_DATA_SEL 0x%08x\n"
> > +		"  MIPI_STATUS 0x%08x\n"
> > +		"  MIPI_IMSC 0x%08x\n",
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
> > +
> > +	return 0;
> > +}
> > +
> > +int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> > +			   struct rkisp1_sensor_async *sensor)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	union phy_configure_opts opts;
> > +	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> > +	s64 pixel_clock;
> > +
> > +	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> > +	if (!pixel_clock) {
> > +		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
> > +		return -EINVAL;
> > +	}
> > +
> > +	phy_mipi_dphy_get_default_config(pixel_clock,
> > +					 rkisp1->isp.sink_fmt->bus_width,
> > +					 sensor->lanes, cfg);
> > +	phy_set_mode(csi->dphy, PHY_MODE_MIPI_DPHY);
> > +	phy_configure(csi->dphy, &opts);
> > +	phy_power_on(csi->dphy);
> > +
> > +	return 0;
> > +}
> > +
> > +void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
> > +{
> > +	phy_power_off(csi->dphy);
> > +}
> > +
> > +void rkisp1_mipi_start(struct rkisp1_csi *csi)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	u32 val;
> > +
> > +	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > +		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
> > +}
> > +
> > +void rkisp1_mipi_stop(struct rkisp1_csi *csi)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	u32 val;
> > +
> > +	/* Mask and clear interrupts. */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> > +
> > +	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > +		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> > +}
> > +
> > +irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
> > +{
> > +	struct device *dev = ctx;
> > +	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
> > +	u32 val, status;
> > +
> > +	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
> > +	if (!status)
> > +		return IRQ_NONE;
> > +
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
> > +
> > +	/*
> > +	 * Disable DPHY errctrl interrupt, because this dphy
> > +	 * erctrl signal is asserted until the next changes
> > +	 * of line state. This time is may be too long and cpu
> > +	 * is hold in this interrupt.
> > +	 */
> > +	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
> > +		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > +		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > +			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
> > +		rkisp1->csi.is_dphy_errctrl_disabled = true;
> > +	}
> > +
> > +	/*
> > +	 * Enable DPHY errctrl interrupt again, if mipi have receive
> > +	 * the whole frame without any error.
> > +	 */
> > +	if (status == RKISP1_CIF_MIPI_FRAME_END) {
> > +		/*
> > +		 * Enable DPHY errctrl interrupt again, if mipi have receive
> > +		 * the whole frame without any error.
> > +		 */
> > +		if (rkisp1->csi.is_dphy_errctrl_disabled) {
> > +			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > +			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
> > +			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
> > +			rkisp1->csi.is_dphy_errctrl_disabled = false;
> > +		}
> > +	} else {
> > +		rkisp1->debug.mipi_error++;
> > +	}
> > +
> > +	return IRQ_HANDLED;
> > +}
> > +
> > +int rkisp1_csi_init(struct rkisp1_device *rkisp1)
> > +{
> > +	struct rkisp1_csi *csi = &rkisp1->csi;
> > +
> > +	csi->dphy = devm_phy_get(rkisp1->dev, "dphy");
> > +	if (IS_ERR(csi->dphy)) {
> > +		if (PTR_ERR(csi->dphy) != -EPROBE_DEFER)
> > +		dev_err_probe(rkisp1->dev, PTR_ERR(csi->dphy),
> > +			      "Couldn't get the MIPI D-PHY\n");
> 
> indentation

Actually it's the if (...) that should be removed, dev_err_probe()
handles that.

> > +		return PTR_ERR(csi->dphy);
> > +	}
> > +
> > +	phy_init(csi->dphy);
> > +
> > +	return 0;
> > +}
> > +
> > +void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1)
> > +{
> > +	struct rkisp1_csi *csi = &rkisp1->csi;
> > +
> > +	phy_exit(csi->dphy);
> > +}
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > new file mode 100644
> > index 000000000000..d97a4ee5c002
> > --- /dev/null
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > @@ -0,0 +1,28 @@
> > +/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
> > +/*
> > + * Rockchip ISP1 Driver - CSI-2 Receiver
> > + *
> > + * Copyright (C) 2019 Collabora, Ltd.
> > + * Copyright (C) 2022 Ideas on Board
> > + *
> > + * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
> > + * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
> > + */
> > +#ifndef _RKISP1_CSI_H
> > +#define _RKISP1_CSI_H
> > +
> > +struct rkisp1_device;
> > +struct rkisp1_sensor_async;
> > +
> > +int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> > +void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> > +
> > +int rkisp1_config_mipi(struct rkisp1_csi *csi);
> > +
> > +int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> > +			   struct rkisp1_sensor_async *sensor);
> > +void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
> > +void rkisp1_mipi_start(struct rkisp1_csi *csi);
> > +void rkisp1_mipi_stop(struct rkisp1_csi *csi);
> 
> some of the functions name here are *_csi_* and some are *_csi2_*
> maybe choose consistent name?

As you noted, this is fixed in a later patch.

> > +
> > +#endif /* _RKISP1_CSI_H */
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index 0f3e45cdbf2a..373a1f00c10a 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -15,11 +15,11 @@
> >  #include <linux/of_graph.h>
> >  #include <linux/of_platform.h>
> >  #include <linux/pinctrl/consumer.h>
> > -#include <linux/phy/phy.h>
> > -#include <linux/phy/phy-mipi-dphy.h>
> > +#include <linux/pm_runtime.h>
> >  #include <media/v4l2-fwnode.h>
> > 
> >  #include "rkisp1-common.h"
> > +#include "rkisp1-csi.h"
> > 
> >  /*
> >   * ISP Details
> > @@ -128,14 +128,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  	}
> > 
> >  	s_asd->sd = sd;
> > -	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
> > -	if (IS_ERR(s_asd->dphy)) {
> > -		if (PTR_ERR(s_asd->dphy) != -EPROBE_DEFER)
> > -			dev_err(rkisp1->dev, "Couldn't get the MIPI D-PHY\n");
> > -		return PTR_ERR(s_asd->dphy);
> > -	}
> > -
> > -	phy_init(s_asd->dphy);
> > 
> >  	/* Create the link to the sensor. */
> >  	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> > @@ -152,16 +144,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> >  }
> > 
> > -static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
> > -					  struct v4l2_subdev *sd,
> > -					  struct v4l2_async_subdev *asd)
> > -{
> > -	struct rkisp1_sensor_async *s_asd =
> > -		container_of(asd, struct rkisp1_sensor_async, asd);
> > -
> > -	phy_exit(s_asd->dphy);
> > -}
> > -
> >  static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> >  {
> >  	struct rkisp1_device *rkisp1 =
> > @@ -180,7 +162,6 @@ static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
> > 
> >  static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> >  	.bound = rkisp1_subdev_notifier_bound,
> > -	.unbind = rkisp1_subdev_notifier_unbind,
> >  	.complete = rkisp1_subdev_notifier_complete,
> >  	.destroy = rkisp1_subdev_notifier_destroy,
> >  };
> > @@ -540,14 +521,20 @@ static int rkisp1_probe(struct platform_device *pdev)
> >  		goto err_unreg_v4l2_dev;
> >  	}
> > 
> > -	ret = rkisp1_entities_register(rkisp1);
> > +	ret = rkisp1_csi_init(rkisp1);
> >  	if (ret)
> >  		goto err_unreg_media_dev;
> > 
> > +	ret = rkisp1_entities_register(rkisp1);
> > +	if (ret)
> > +		goto err_cleanup_csi;
> > +
> >  	rkisp1_debug_init(rkisp1);
> > 
> >  	return 0;
> > 
> > +err_cleanup_csi:
> > +	rkisp1_csi_cleanup(rkisp1);
> >  err_unreg_media_dev:
> >  	media_device_unregister(&rkisp1->media_dev);
> >  err_unreg_v4l2_dev:
> > @@ -565,6 +552,7 @@ static int rkisp1_remove(struct platform_device *pdev)
> >  	v4l2_async_nf_cleanup(&rkisp1->notifier);
> > 
> >  	rkisp1_entities_unregister(rkisp1);
> > +	rkisp1_csi_cleanup(rkisp1);
> >  	rkisp1_debug_cleanup(rkisp1);
> > 
> >  	media_device_unregister(&rkisp1->media_dev);
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > index 81138c676ac0..5eabb321e320 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > @@ -9,8 +9,6 @@
> >   */
> > 
> >  #include <linux/iopoll.h>
> > -#include <linux/phy/phy.h>
> > -#include <linux/phy/phy-mipi-dphy.h>
> >  #include <linux/pm_runtime.h>
> >  #include <linux/videodev2.h>
> >  #include <linux/vmalloc.h>
> > @@ -18,6 +16,7 @@
> >  #include <media/v4l2-event.h>
> > 
> >  #include "rkisp1-common.h"
> > +#include "rkisp1-csi.h"
> > 
> >  #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> >  #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
> > @@ -265,55 +264,6 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> >  	return 0;
> >  }
> > 
> > -static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
> > -{
> > -	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> > -	unsigned int lanes = rkisp1->active_sensor->lanes;
> > -	u32 mipi_ctrl;
> > -
> > -	if (lanes < 1 || lanes > 4)
> > -		return -EINVAL;
> > -
> > -	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
> > -		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
> > -		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
> > -		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
> > -
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
> > -
> > -	/* V12 could also use a newer csi2-host, but we don't want that yet */
> > -	if (rkisp1->info->isp_ver == RKISP1_V12)
> > -		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
> > -
> > -	/* Configure Data Type and Virtual Channel */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
> > -		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
> > -		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
> > -
> > -	/* Clear MIPI interrupts */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> > -	/*
> > -	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
> > -	 * isp bus may be dead when switch isp.
> > -	 */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > -		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
> > -		     RKISP1_CIF_MIPI_ERR_DPHY |
> > -		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
> > -		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
> > -
> > -	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
> > -		"  MIPI_IMG_DATA_SEL 0x%08x\n"
> > -		"  MIPI_STATUS 0x%08x\n"
> > -		"  MIPI_IMSC 0x%08x\n",
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
> > -
> > -	return 0;
> > -}
> > -
> >  /* Configure MUX */
> >  static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> >  {
> > @@ -326,7 +276,7 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> >  		ret = rkisp1_config_dvp(rkisp1);
> >  		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> >  	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
> > -		ret = rkisp1_config_mipi(rkisp1);
> > +		ret = rkisp1_config_mipi(&rkisp1->csi);
> >  		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> >  	}
> > 
> > @@ -360,17 +310,14 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> >  	 * Stop ISP(isp) ->wait for ISP isp off
> >  	 */
> >  	/* stop and clear MI, MIPI, and ISP interrupts */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> > -
> >  	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
> >  	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
> > 
> >  	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
> >  	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
> > -	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > -		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> > +
> > +	rkisp1_mipi_stop(&rkisp1->csi);
> > +
> >  	/* stop ISP */
> >  	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> >  	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
> > @@ -417,11 +364,9 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> >  	rkisp1_config_clk(rkisp1);
> > 
> >  	/* Activate MIPI */
> > -	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
> > -		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > -		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > -			     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
> > -	}
> > +	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
> > +		rkisp1_mipi_start(&rkisp1->csi);
> > +
> >  	/* Activate ISP */
> >  	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> >  	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
> > @@ -814,35 +759,6 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
> >   * Stream operations
> >   */
> > 
> > -static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
> > -				  struct rkisp1_sensor_async *sensor)
> > -{
> > -	struct rkisp1_device *rkisp1 =
> > -		container_of(isp->sd.v4l2_dev, struct rkisp1_device, v4l2_dev);
> > -	union phy_configure_opts opts;
> > -	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> > -	s64 pixel_clock;
> > -
> > -	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> > -	if (!pixel_clock) {
> > -		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
> > -		return -EINVAL;
> > -	}
> > -
> > -	phy_mipi_dphy_get_default_config(pixel_clock, isp->sink_fmt->bus_width,
> > -					 sensor->lanes, cfg);
> > -	phy_set_mode(sensor->dphy, PHY_MODE_MIPI_DPHY);
> > -	phy_configure(sensor->dphy, &opts);
> > -	phy_power_on(sensor->dphy);
> > -
> > -	return 0;
> > -}
> > -
> > -static void rkisp1_mipi_csi2_stop(struct rkisp1_sensor_async *sensor)
> > -{
> > -	phy_power_off(sensor->dphy);
> > -}
> > -
> >  static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  {
> >  	struct rkisp1_device *rkisp1 =
> > @@ -856,7 +772,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  				 false);
> > 
> >  		rkisp1_isp_stop(rkisp1);
> > -		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
> > +		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> >  		return 0;
> >  	}
> > 
> > @@ -878,7 +794,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  	if (ret)
> >  		goto mutex_unlock;
> > 
> > -	ret = rkisp1_mipi_csi2_start(&rkisp1->isp, rkisp1->active_sensor);
> > +	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
> >  	if (ret)
> >  		goto mutex_unlock;
> > 
> > @@ -888,7 +804,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  			       true);
> >  	if (ret) {
> >  		rkisp1_isp_stop(rkisp1);
> > -		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
> > +		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> >  		goto mutex_unlock;
> >  	}
> > 
> > @@ -993,53 +909,6 @@ void rkisp1_isp_unregister(struct rkisp1_device *rkisp1)
> >   * Interrupt handlers
> >   */
> > 
> > -irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
> > -{
> > -	struct device *dev = ctx;
> > -	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
> > -	u32 val, status;
> > -
> > -	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
> > -	if (!status)
> > -		return IRQ_NONE;
> > -
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
> > -
> > -	/*
> > -	 * Disable DPHY errctrl interrupt, because this dphy
> > -	 * erctrl signal is asserted until the next changes
> > -	 * of line state. This time is may be too long and cpu
> > -	 * is hold in this interrupt.
> > -	 */
> > -	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
> > -		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > -		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > -			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
> > -		rkisp1->isp.is_dphy_errctrl_disabled = true;
> > -	}
> > -
> > -	/*
> > -	 * Enable DPHY errctrl interrupt again, if mipi have receive
> > -	 * the whole frame without any error.
> > -	 */
> > -	if (status == RKISP1_CIF_MIPI_FRAME_END) {
> > -		/*
> > -		 * Enable DPHY errctrl interrupt again, if mipi have receive
> > -		 * the whole frame without any error.
> > -		 */
> > -		if (rkisp1->isp.is_dphy_errctrl_disabled) {
> > -			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > -			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
> > -			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
> > -			rkisp1->isp.is_dphy_errctrl_disabled = false;
> > -		}
> > -	} else {
> > -		rkisp1->debug.mipi_error++;
> > -	}
> > -
> > -	return IRQ_HANDLED;
> > -}
> > -
> >  static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
> >  {
> >  	struct v4l2_event event = {

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 18/55] media: rkisp1: Split CSI handling to separate file
@ 2022-06-25 10:18       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 10:18 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Sat, Jun 25, 2022 at 06:48:54AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:10, Paul Elder wrote:
> > Not all ISP instances include a MIPI CSI-2 receiver. To prepare for
> > making it optional, move code related to the CSI-2 receiver to a
> > separate file.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../media/platform/rockchip/rkisp1/Makefile   |   1 +
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 +-
> >  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 193 ++++++++++++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  28 +++
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  32 +--
> >  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 153 +-------------
> >  6 files changed, 257 insertions(+), 167 deletions(-)
> >  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >  create mode 100644 drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/Makefile b/drivers/media/platform/rockchip/rkisp1/Makefile
> > index f7543a82aa10..b3844c4f7623 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/Makefile
> > +++ b/drivers/media/platform/rockchip/rkisp1/Makefile
> > @@ -2,6 +2,7 @@
> > 
> >  rockchip-isp1-y := rkisp1-capture.o \
> >  		   rkisp1-common.o \
> > +		   rkisp1-csi.o \
> >  		   rkisp1-dev.o \
> >  		   rkisp1-isp.o \
> >  		   rkisp1-resizer.o \
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index 60c5462e1746..a52fa9e0dd66 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -123,7 +123,6 @@ struct rkisp1_info {
> >   * @mbus_flags:		media bus (V4L2_MBUS_*) flags
> >   * @sd:			a pointer to v4l2_subdev struct of the sensor
> >   * @pixel_rate_ctrl:	pixel rate of the sensor, used to initialize the phy
> > - * @dphy:		a pointer to the phy
> >   */
> >  struct rkisp1_sensor_async {
> >  	struct v4l2_async_subdev asd;
> > @@ -134,7 +133,19 @@ struct rkisp1_sensor_async {
> >  	unsigned int mbus_flags;
> >  	struct v4l2_subdev *sd;
> >  	struct v4l2_ctrl *pixel_rate_ctrl;
> > +};
> > +
> > +/*
> > + * struct rkisp1_csi - CSI receiver subdev
> > + *
> > + * @rkisp1: pointer to the rkisp1 device
> > + * @dphy: a pointer to the phy
> > + * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
> > + */
> > +struct rkisp1_csi {
> > +	struct rkisp1_device *rkisp1;
> 
> I think you missed initializing csi->rkips1

Indeed. It's probably fixed in a later patch as the series doesn't
crash, but I'll fix it here.

> >  	struct phy *dphy;
> > +	bool is_dphy_errctrl_disabled;
> >  };
> > 
> >  /*
> > @@ -147,7 +158,6 @@ struct rkisp1_sensor_async {
> >   * @sink_fmt:			input format
> >   * @src_fmt:			output format
> >   * @ops_lock:			ops serialization
> > - * @is_dphy_errctrl_disabled:	if dphy errctrl is disabled (avoid endless interrupt)
> >   * @frame_sequence:		used to synchronize frame_id between video devices.
> >   */
> >  struct rkisp1_isp {
> > @@ -157,7 +167,6 @@ struct rkisp1_isp {
> >  	const struct rkisp1_mbus_info *sink_fmt;
> >  	const struct rkisp1_mbus_info *src_fmt;
> >  	struct mutex ops_lock; /* serialize the subdevice ops */
> > -	bool is_dphy_errctrl_disabled;
> >  	__u32 frame_sequence;
> >  };
> > 
> > @@ -411,6 +420,7 @@ struct rkisp1_debug {
> >   * @media_dev:	   media_device variable
> >   * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
> >   * @active_sensor: sensor in-use, set when streaming on
> > + * @csi:	   internal CSI-2 receiver
> >   * @isp:	   ISP sub-device
> >   * @resizer_devs:  resizer sub-devices
> >   * @capture_devs:  capture devices
> > @@ -430,6 +440,7 @@ struct rkisp1_device {
> >  	struct media_device media_dev;
> >  	struct v4l2_async_notifier notifier;
> >  	struct rkisp1_sensor_async *active_sensor;
> > +	struct rkisp1_csi csi;
> >  	struct rkisp1_isp isp;
> >  	struct rkisp1_resizer resizer_devs[2];
> >  	struct rkisp1_capture capture_devs[2];
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > new file mode 100644
> > index 000000000000..4af04296b625
> > --- /dev/null
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > @@ -0,0 +1,193 @@
> > +// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
> > +/*
> > + * Rockchip ISP1 Driver - CSI-2 Receiver
> > + *
> > + * Copyright (C) 2019 Collabora, Ltd.
> > + * Copyright (C) 2022 Ideas on Board
> > + *
> > + * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
> > + * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
> > + */
> > +
> > +#include <linux/device.h>
> > +#include <linux/phy/phy.h>
> > +#include <linux/phy/phy-mipi-dphy.h>
> > +
> > +#include <media/v4l2-ctrls.h>
> > +
> > +#include "rkisp1-common.h"
> > +#include "rkisp1-csi.h"
> > +
> > +int rkisp1_config_mipi(struct rkisp1_csi *csi)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> > +	unsigned int lanes = rkisp1->active_sensor->lanes;
> > +	u32 mipi_ctrl;
> > +
> > +	if (lanes < 1 || lanes > 4)
> > +		return -EINVAL;
> > +
> > +	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
> > +		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
> > +		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
> > +		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
> > +
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
> > +
> > +	/* V12 could also use a newer csi2-host, but we don't want that yet */
> > +	if (rkisp1->info->isp_ver == RKISP1_V12)
> > +		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
> > +
> > +	/* Configure Data Type and Virtual Channel */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
> > +		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
> > +		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
> > +
> > +	/* Clear MIPI interrupts */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> 
> new line here

The new line was already missing, but as this patch contains more than
just a code move, I'll fix it here instead of in a separate patch.

> > +	/*
> > +	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
> > +	 * isp bus may be dead when switch isp.
> > +	 */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > +		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
> > +		     RKISP1_CIF_MIPI_ERR_DPHY |
> > +		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
> > +		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
> > +
> > +	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
> > +		"  MIPI_IMG_DATA_SEL 0x%08x\n"
> > +		"  MIPI_STATUS 0x%08x\n"
> > +		"  MIPI_IMSC 0x%08x\n",
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
> > +		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
> > +
> > +	return 0;
> > +}
> > +
> > +int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> > +			   struct rkisp1_sensor_async *sensor)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	union phy_configure_opts opts;
> > +	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> > +	s64 pixel_clock;
> > +
> > +	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> > +	if (!pixel_clock) {
> > +		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
> > +		return -EINVAL;
> > +	}
> > +
> > +	phy_mipi_dphy_get_default_config(pixel_clock,
> > +					 rkisp1->isp.sink_fmt->bus_width,
> > +					 sensor->lanes, cfg);
> > +	phy_set_mode(csi->dphy, PHY_MODE_MIPI_DPHY);
> > +	phy_configure(csi->dphy, &opts);
> > +	phy_power_on(csi->dphy);
> > +
> > +	return 0;
> > +}
> > +
> > +void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi)
> > +{
> > +	phy_power_off(csi->dphy);
> > +}
> > +
> > +void rkisp1_mipi_start(struct rkisp1_csi *csi)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	u32 val;
> > +
> > +	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > +		     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
> > +}
> > +
> > +void rkisp1_mipi_stop(struct rkisp1_csi *csi)
> > +{
> > +	struct rkisp1_device *rkisp1 = csi->rkisp1;
> > +	u32 val;
> > +
> > +	/* Mask and clear interrupts. */
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> > +
> > +	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > +		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> > +}
> > +
> > +irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
> > +{
> > +	struct device *dev = ctx;
> > +	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
> > +	u32 val, status;
> > +
> > +	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
> > +	if (!status)
> > +		return IRQ_NONE;
> > +
> > +	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
> > +
> > +	/*
> > +	 * Disable DPHY errctrl interrupt, because this dphy
> > +	 * erctrl signal is asserted until the next changes
> > +	 * of line state. This time is may be too long and cpu
> > +	 * is hold in this interrupt.
> > +	 */
> > +	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
> > +		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > +		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > +			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
> > +		rkisp1->csi.is_dphy_errctrl_disabled = true;
> > +	}
> > +
> > +	/*
> > +	 * Enable DPHY errctrl interrupt again, if mipi have receive
> > +	 * the whole frame without any error.
> > +	 */
> > +	if (status == RKISP1_CIF_MIPI_FRAME_END) {
> > +		/*
> > +		 * Enable DPHY errctrl interrupt again, if mipi have receive
> > +		 * the whole frame without any error.
> > +		 */
> > +		if (rkisp1->csi.is_dphy_errctrl_disabled) {
> > +			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > +			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
> > +			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
> > +			rkisp1->csi.is_dphy_errctrl_disabled = false;
> > +		}
> > +	} else {
> > +		rkisp1->debug.mipi_error++;
> > +	}
> > +
> > +	return IRQ_HANDLED;
> > +}
> > +
> > +int rkisp1_csi_init(struct rkisp1_device *rkisp1)
> > +{
> > +	struct rkisp1_csi *csi = &rkisp1->csi;
> > +
> > +	csi->dphy = devm_phy_get(rkisp1->dev, "dphy");
> > +	if (IS_ERR(csi->dphy)) {
> > +		if (PTR_ERR(csi->dphy) != -EPROBE_DEFER)
> > +		dev_err_probe(rkisp1->dev, PTR_ERR(csi->dphy),
> > +			      "Couldn't get the MIPI D-PHY\n");
> 
> indentation

Actually it's the if (...) that should be removed, dev_err_probe()
handles that.

> > +		return PTR_ERR(csi->dphy);
> > +	}
> > +
> > +	phy_init(csi->dphy);
> > +
> > +	return 0;
> > +}
> > +
> > +void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1)
> > +{
> > +	struct rkisp1_csi *csi = &rkisp1->csi;
> > +
> > +	phy_exit(csi->dphy);
> > +}
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > new file mode 100644
> > index 000000000000..d97a4ee5c002
> > --- /dev/null
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > @@ -0,0 +1,28 @@
> > +/* SPDX-License-Identifier: (GPL-2.0+ OR MIT) */
> > +/*
> > + * Rockchip ISP1 Driver - CSI-2 Receiver
> > + *
> > + * Copyright (C) 2019 Collabora, Ltd.
> > + * Copyright (C) 2022 Ideas on Board
> > + *
> > + * Based on Rockchip ISP1 driver by Rockchip Electronics Co., Ltd.
> > + * Copyright (C) 2017 Rockchip Electronics Co., Ltd.
> > + */
> > +#ifndef _RKISP1_CSI_H
> > +#define _RKISP1_CSI_H
> > +
> > +struct rkisp1_device;
> > +struct rkisp1_sensor_async;
> > +
> > +int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> > +void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> > +
> > +int rkisp1_config_mipi(struct rkisp1_csi *csi);
> > +
> > +int rkisp1_mipi_csi2_start(struct rkisp1_csi *csi,
> > +			   struct rkisp1_sensor_async *sensor);
> > +void rkisp1_mipi_csi2_stop(struct rkisp1_csi *csi);
> > +void rkisp1_mipi_start(struct rkisp1_csi *csi);
> > +void rkisp1_mipi_stop(struct rkisp1_csi *csi);
> 
> some of the functions name here are *_csi_* and some are *_csi2_*
> maybe choose consistent name?

As you noted, this is fixed in a later patch.

> > +
> > +#endif /* _RKISP1_CSI_H */
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index 0f3e45cdbf2a..373a1f00c10a 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -15,11 +15,11 @@
> >  #include <linux/of_graph.h>
> >  #include <linux/of_platform.h>
> >  #include <linux/pinctrl/consumer.h>
> > -#include <linux/phy/phy.h>
> > -#include <linux/phy/phy-mipi-dphy.h>
> > +#include <linux/pm_runtime.h>
> >  #include <media/v4l2-fwnode.h>
> > 
> >  #include "rkisp1-common.h"
> > +#include "rkisp1-csi.h"
> > 
> >  /*
> >   * ISP Details
> > @@ -128,14 +128,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  	}
> > 
> >  	s_asd->sd = sd;
> > -	s_asd->dphy = devm_phy_get(rkisp1->dev, "dphy");
> > -	if (IS_ERR(s_asd->dphy)) {
> > -		if (PTR_ERR(s_asd->dphy) != -EPROBE_DEFER)
> > -			dev_err(rkisp1->dev, "Couldn't get the MIPI D-PHY\n");
> > -		return PTR_ERR(s_asd->dphy);
> > -	}
> > -
> > -	phy_init(s_asd->dphy);
> > 
> >  	/* Create the link to the sensor. */
> >  	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> > @@ -152,16 +144,6 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> >  }
> > 
> > -static void rkisp1_subdev_notifier_unbind(struct v4l2_async_notifier *notifier,
> > -					  struct v4l2_subdev *sd,
> > -					  struct v4l2_async_subdev *asd)
> > -{
> > -	struct rkisp1_sensor_async *s_asd =
> > -		container_of(asd, struct rkisp1_sensor_async, asd);
> > -
> > -	phy_exit(s_asd->dphy);
> > -}
> > -
> >  static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> >  {
> >  	struct rkisp1_device *rkisp1 =
> > @@ -180,7 +162,6 @@ static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
> > 
> >  static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> >  	.bound = rkisp1_subdev_notifier_bound,
> > -	.unbind = rkisp1_subdev_notifier_unbind,
> >  	.complete = rkisp1_subdev_notifier_complete,
> >  	.destroy = rkisp1_subdev_notifier_destroy,
> >  };
> > @@ -540,14 +521,20 @@ static int rkisp1_probe(struct platform_device *pdev)
> >  		goto err_unreg_v4l2_dev;
> >  	}
> > 
> > -	ret = rkisp1_entities_register(rkisp1);
> > +	ret = rkisp1_csi_init(rkisp1);
> >  	if (ret)
> >  		goto err_unreg_media_dev;
> > 
> > +	ret = rkisp1_entities_register(rkisp1);
> > +	if (ret)
> > +		goto err_cleanup_csi;
> > +
> >  	rkisp1_debug_init(rkisp1);
> > 
> >  	return 0;
> > 
> > +err_cleanup_csi:
> > +	rkisp1_csi_cleanup(rkisp1);
> >  err_unreg_media_dev:
> >  	media_device_unregister(&rkisp1->media_dev);
> >  err_unreg_v4l2_dev:
> > @@ -565,6 +552,7 @@ static int rkisp1_remove(struct platform_device *pdev)
> >  	v4l2_async_nf_cleanup(&rkisp1->notifier);
> > 
> >  	rkisp1_entities_unregister(rkisp1);
> > +	rkisp1_csi_cleanup(rkisp1);
> >  	rkisp1_debug_cleanup(rkisp1);
> > 
> >  	media_device_unregister(&rkisp1->media_dev);
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > index 81138c676ac0..5eabb321e320 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > @@ -9,8 +9,6 @@
> >   */
> > 
> >  #include <linux/iopoll.h>
> > -#include <linux/phy/phy.h>
> > -#include <linux/phy/phy-mipi-dphy.h>
> >  #include <linux/pm_runtime.h>
> >  #include <linux/videodev2.h>
> >  #include <linux/vmalloc.h>
> > @@ -18,6 +16,7 @@
> >  #include <media/v4l2-event.h>
> > 
> >  #include "rkisp1-common.h"
> > +#include "rkisp1-csi.h"
> > 
> >  #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> >  #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
> > @@ -265,55 +264,6 @@ static int rkisp1_config_dvp(struct rkisp1_device *rkisp1)
> >  	return 0;
> >  }
> > 
> > -static int rkisp1_config_mipi(struct rkisp1_device *rkisp1)
> > -{
> > -	const struct rkisp1_mbus_info *sink_fmt = rkisp1->isp.sink_fmt;
> > -	unsigned int lanes = rkisp1->active_sensor->lanes;
> > -	u32 mipi_ctrl;
> > -
> > -	if (lanes < 1 || lanes > 4)
> > -		return -EINVAL;
> > -
> > -	mipi_ctrl = RKISP1_CIF_MIPI_CTRL_NUM_LANES(lanes - 1) |
> > -		    RKISP1_CIF_MIPI_CTRL_SHUTDOWNLANES(0xf) |
> > -		    RKISP1_CIF_MIPI_CTRL_ERR_SOT_SYNC_HS_SKIP |
> > -		    RKISP1_CIF_MIPI_CTRL_CLOCKLANE_ENA;
> > -
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL, mipi_ctrl);
> > -
> > -	/* V12 could also use a newer csi2-host, but we don't want that yet */
> > -	if (rkisp1->info->isp_ver == RKISP1_V12)
> > -		rkisp1_write(rkisp1, RKISP1_CIF_ISP_CSI0_CTRL0, 0);
> > -
> > -	/* Configure Data Type and Virtual Channel */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL,
> > -		     RKISP1_CIF_MIPI_DATA_SEL_DT(sink_fmt->mipi_dt) |
> > -		     RKISP1_CIF_MIPI_DATA_SEL_VC(0));
> > -
> > -	/* Clear MIPI interrupts */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> > -	/*
> > -	 * Disable RKISP1_CIF_MIPI_ERR_DPHY interrupt here temporary for
> > -	 * isp bus may be dead when switch isp.
> > -	 */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > -		     RKISP1_CIF_MIPI_FRAME_END | RKISP1_CIF_MIPI_ERR_CSI |
> > -		     RKISP1_CIF_MIPI_ERR_DPHY |
> > -		     RKISP1_CIF_MIPI_SYNC_FIFO_OVFLW(0x03) |
> > -		     RKISP1_CIF_MIPI_ADD_DATA_OVFLW);
> > -
> > -	dev_dbg(rkisp1->dev, "\n  MIPI_CTRL 0x%08x\n"
> > -		"  MIPI_IMG_DATA_SEL 0x%08x\n"
> > -		"  MIPI_STATUS 0x%08x\n"
> > -		"  MIPI_IMSC 0x%08x\n",
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL),
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMG_DATA_SEL),
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_STATUS),
> > -		rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC));
> > -
> > -	return 0;
> > -}
> > -
> >  /* Configure MUX */
> >  static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> >  {
> > @@ -326,7 +276,7 @@ static int rkisp1_config_path(struct rkisp1_device *rkisp1)
> >  		ret = rkisp1_config_dvp(rkisp1);
> >  		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_PARALLEL;
> >  	} else if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
> > -		ret = rkisp1_config_mipi(rkisp1);
> > +		ret = rkisp1_config_mipi(&rkisp1->csi);
> >  		dpcl |= RKISP1_CIF_VI_DPCL_IF_SEL_MIPI;
> >  	}
> > 
> > @@ -360,17 +310,14 @@ static void rkisp1_isp_stop(struct rkisp1_device *rkisp1)
> >  	 * Stop ISP(isp) ->wait for ISP isp off
> >  	 */
> >  	/* stop and clear MI, MIPI, and ISP interrupts */
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, 0);
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, ~0);
> > -
> >  	rkisp1_write(rkisp1, RKISP1_CIF_ISP_IMSC, 0);
> >  	rkisp1_write(rkisp1, RKISP1_CIF_ISP_ICR, ~0);
> > 
> >  	rkisp1_write(rkisp1, RKISP1_CIF_MI_IMSC, 0);
> >  	rkisp1_write(rkisp1, RKISP1_CIF_MI_ICR, ~0);
> > -	val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > -		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> > +
> > +	rkisp1_mipi_stop(&rkisp1->csi);
> > +
> >  	/* stop ISP */
> >  	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> >  	val &= ~(RKISP1_CIF_ISP_CTRL_ISP_INFORM_ENABLE |
> > @@ -417,11 +364,9 @@ static void rkisp1_isp_start(struct rkisp1_device *rkisp1)
> >  	rkisp1_config_clk(rkisp1);
> > 
> >  	/* Activate MIPI */
> > -	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY) {
> > -		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_CTRL);
> > -		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_CTRL,
> > -			     val | RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA);
> > -	}
> > +	if (sensor->mbus_type == V4L2_MBUS_CSI2_DPHY)
> > +		rkisp1_mipi_start(&rkisp1->csi);
> > +
> >  	/* Activate ISP */
> >  	val = rkisp1_read(rkisp1, RKISP1_CIF_ISP_CTRL);
> >  	val |= RKISP1_CIF_ISP_CTRL_ISP_CFG_UPD |
> > @@ -814,35 +759,6 @@ static const struct v4l2_subdev_pad_ops rkisp1_isp_pad_ops = {
> >   * Stream operations
> >   */
> > 
> > -static int rkisp1_mipi_csi2_start(struct rkisp1_isp *isp,
> > -				  struct rkisp1_sensor_async *sensor)
> > -{
> > -	struct rkisp1_device *rkisp1 =
> > -		container_of(isp->sd.v4l2_dev, struct rkisp1_device, v4l2_dev);
> > -	union phy_configure_opts opts;
> > -	struct phy_configure_opts_mipi_dphy *cfg = &opts.mipi_dphy;
> > -	s64 pixel_clock;
> > -
> > -	pixel_clock = v4l2_ctrl_g_ctrl_int64(sensor->pixel_rate_ctrl);
> > -	if (!pixel_clock) {
> > -		dev_err(rkisp1->dev, "Invalid pixel rate value\n");
> > -		return -EINVAL;
> > -	}
> > -
> > -	phy_mipi_dphy_get_default_config(pixel_clock, isp->sink_fmt->bus_width,
> > -					 sensor->lanes, cfg);
> > -	phy_set_mode(sensor->dphy, PHY_MODE_MIPI_DPHY);
> > -	phy_configure(sensor->dphy, &opts);
> > -	phy_power_on(sensor->dphy);
> > -
> > -	return 0;
> > -}
> > -
> > -static void rkisp1_mipi_csi2_stop(struct rkisp1_sensor_async *sensor)
> > -{
> > -	phy_power_off(sensor->dphy);
> > -}
> > -
> >  static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  {
> >  	struct rkisp1_device *rkisp1 =
> > @@ -856,7 +772,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  				 false);
> > 
> >  		rkisp1_isp_stop(rkisp1);
> > -		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
> > +		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> >  		return 0;
> >  	}
> > 
> > @@ -878,7 +794,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  	if (ret)
> >  		goto mutex_unlock;
> > 
> > -	ret = rkisp1_mipi_csi2_start(&rkisp1->isp, rkisp1->active_sensor);
> > +	ret = rkisp1_mipi_csi2_start(&rkisp1->csi, rkisp1->active_sensor);
> >  	if (ret)
> >  		goto mutex_unlock;
> > 
> > @@ -888,7 +804,7 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  			       true);
> >  	if (ret) {
> >  		rkisp1_isp_stop(rkisp1);
> > -		rkisp1_mipi_csi2_stop(rkisp1->active_sensor);
> > +		rkisp1_mipi_csi2_stop(&rkisp1->csi);
> >  		goto mutex_unlock;
> >  	}
> > 
> > @@ -993,53 +909,6 @@ void rkisp1_isp_unregister(struct rkisp1_device *rkisp1)
> >   * Interrupt handlers
> >   */
> > 
> > -irqreturn_t rkisp1_mipi_isr(int irq, void *ctx)
> > -{
> > -	struct device *dev = ctx;
> > -	struct rkisp1_device *rkisp1 = dev_get_drvdata(dev);
> > -	u32 val, status;
> > -
> > -	status = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_MIS);
> > -	if (!status)
> > -		return IRQ_NONE;
> > -
> > -	rkisp1_write(rkisp1, RKISP1_CIF_MIPI_ICR, status);
> > -
> > -	/*
> > -	 * Disable DPHY errctrl interrupt, because this dphy
> > -	 * erctrl signal is asserted until the next changes
> > -	 * of line state. This time is may be too long and cpu
> > -	 * is hold in this interrupt.
> > -	 */
> > -	if (status & RKISP1_CIF_MIPI_ERR_CTRL(0x0f)) {
> > -		val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > -		rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC,
> > -			     val & ~RKISP1_CIF_MIPI_ERR_CTRL(0x0f));
> > -		rkisp1->isp.is_dphy_errctrl_disabled = true;
> > -	}
> > -
> > -	/*
> > -	 * Enable DPHY errctrl interrupt again, if mipi have receive
> > -	 * the whole frame without any error.
> > -	 */
> > -	if (status == RKISP1_CIF_MIPI_FRAME_END) {
> > -		/*
> > -		 * Enable DPHY errctrl interrupt again, if mipi have receive
> > -		 * the whole frame without any error.
> > -		 */
> > -		if (rkisp1->isp.is_dphy_errctrl_disabled) {
> > -			val = rkisp1_read(rkisp1, RKISP1_CIF_MIPI_IMSC);
> > -			val |= RKISP1_CIF_MIPI_ERR_CTRL(0x0f);
> > -			rkisp1_write(rkisp1, RKISP1_CIF_MIPI_IMSC, val);
> > -			rkisp1->isp.is_dphy_errctrl_disabled = false;
> > -		}
> > -	} else {
> > -		rkisp1->debug.mipi_error++;
> > -	}
> > -
> > -	return IRQ_HANDLED;
> > -}
> > -
> >  static void rkisp1_isp_queue_event_sof(struct rkisp1_isp *isp)
> >  {
> >  	struct v4l2_event event = {

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
  2022-06-25  7:00     ` Dafna Hirschfeld
@ 2022-06-25 11:03       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 11:03 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Sat, Jun 25, 2022 at 10:00:34AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:11, Paul Elder wrote:
> >The CSI receiver is a component separate from the ISP or the resizers.
> >It is actually optional, not all device model include a CSI receiver. On
> >some SoCs CSI-2 support can be provided through an external CSI-2
> >receiver, connected to the ISP's parallel input.
> >
> >To support those use cases, create a V4L2 subdev to model the CSI
> >receiver. It will allow the driver to handle both internal and external
> >CSI receivers the same way.
> >
> >The next commit will plumb the CSI subdev to the rest of the driver,
> >replacing direct function calls.
> >
> >Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> >Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >---
> > .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
> > .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
> > .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
> > .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
> > 4 files changed, 313 insertions(+)
> >
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >index 3c55e922346e..0ab49d1feb55 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
> > 	RKISP1_RSZ_PAD_MAX
> > };
> >
> >+/* enum for the csi receiver pads */
> >+enum rkisp1_csi_pad {
> >+	RKISP1_CSI_PAD_SINK,
> >+	RKISP1_CSI_PAD_SRC,
> >+	RKISP1_CSI_PAD_MAX
> 
> I'd call it RKISP1_CSI_PAD_NUM

OK.

> >+};
> >+
> > /* enum for the capture id */
> > enum rkisp1_stream_id {
> > 	RKISP1_MAINPATH,
> >@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
> >  * @rkisp1: pointer to the rkisp1 device
> >  * @dphy: a pointer to the phy
> >  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
> >+ * @sd: v4l2_subdev variable
> >+ * @pads: media pads
> >+ * @pad_cfg: configurations for the pads
> >+ * @ops_lock: a lock for the subdev ops
> >+ * @source: source in-use, set when starting streaming
> >  */
> > struct rkisp1_csi {
> > 	struct rkisp1_device *rkisp1;
> > 	struct phy *dphy;
> > 	bool is_dphy_errctrl_disabled;
> >+	struct v4l2_subdev sd;
> >+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
> >+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
> >+	struct mutex ops_lock; /* serialize the subdevice ops */
> >+	struct rkisp1_sensor_async *source;
> > };
> >
> > /*
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >index 425a3b014089..8182694a6fe0 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >@@ -15,10 +15,34 @@
> > #include <linux/phy/phy-mipi-dphy.h>
> >
> > #include <media/v4l2-ctrls.h>
> >+#include <media/v4l2-fwnode.h>
> >
> > #include "rkisp1-common.h"
> > #include "rkisp1-csi.h"
> >
> >+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
> >+
> >+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
> >+
> >+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
> >+{
> >+	return container_of(sd, struct rkisp1_csi, sd);
> >+}
> >+
> >+static struct v4l2_mbus_framefmt *
> >+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
> >+		       struct v4l2_subdev_state *sd_state,
> >+		       unsigned int pad, u32 which)
> >+{
> >+	struct v4l2_subdev_state state = {
> >+		.pads = csi->pad_cfg
> >+	};
> 
> newline here

I'm surprised checkpatch didn't warn. Fixed.

> >+	if (which == V4L2_SUBDEV_FORMAT_TRY)
> >+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
> >+	else
> >+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
> >+}
> >+
> > static int rkisp1_csi_config(struct rkisp1_csi *csi,
> > 			     const struct rkisp1_sensor_async *sensor)
> > {
> >@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
> > 	return IRQ_HANDLED;
> > }
> >
> >+/* ----------------------------------------------------------------------------
> >+ * Subdev pad operations
> >+ */
> >+
> >+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
> >+				   struct v4l2_subdev_state *sd_state,
> >+				   struct v4l2_mbus_framefmt *format,
> >+				   unsigned int which)
> >+{
> >+	struct v4l2_mbus_framefmt *sink_fmt;
> >+
> >+	/* We don't set the src format directly; take it from the sink format */
> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
> >+					  which);
> >+
> >+	*format = *sink_fmt;
> >+}
> >+
> >+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
> >+				    struct v4l2_subdev_state *sd_state,
> >+				    struct v4l2_mbus_framefmt *format,
> >+				    unsigned int which)
> >+{
> >+	const struct rkisp1_mbus_info *mbus_info;
> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
> >+
> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
> >+					  which);
> >+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
> >+					 which);
> >+
> >+	sink_fmt->code = format->code;
> >+
> >+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> >+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
> >+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
> >+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> >+	}
> >+
> >+	sink_fmt->width = clamp_t(u32, format->width,
> >+				  RKISP1_ISP_MIN_WIDTH,
> >+				  RKISP1_ISP_MAX_WIDTH);
> >+	sink_fmt->height = clamp_t(u32, format->height,
> >+				   RKISP1_ISP_MIN_HEIGHT,
> >+				   RKISP1_ISP_MAX_HEIGHT);
> >+
> >+	/* Propagate to source pad */
> >+	src_fmt->code = sink_fmt->code;
> >+	src_fmt->width = sink_fmt->width;
> >+	src_fmt->height = sink_fmt->height;
> >+
> 
> why here you don't do '*src_fmt = *sink_fmt' instead of per field propaget ?

You're right, the CSI-2 receiver doesn't change the format in any way,
that would be easier.

> >+	*format = *sink_fmt;
> >+}
> >+
> >+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
> >+				     struct v4l2_subdev_state *sd_state,
> >+				     struct v4l2_subdev_mbus_code_enum *code)
> >+{
> >+	unsigned int i;
> >+	int pos = 0;
> >+
> >+	if (code->index >= rkisp1_mbus_info_length())
> >+		return -EINVAL;
> >+
> >+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
> >+		const struct rkisp1_mbus_info *fmt =
> >+			rkisp1_mbus_info_get_by_index(i);
> >+
> >+		if (fmt->direction & RKISP1_ISP_SD_SINK)
> >+			pos++;
> >+
> >+		if (code->index == pos - 1) {
> >+			code->code = fmt->mbus_code;
> >+			return 0;
> >+		}
> >+	}
> >+
> >+	return -EINVAL;
> >+}
> >+
> >+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
> >+				  struct v4l2_subdev_state *sd_state)
> >+{
> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
> >+
> >+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
> >+					      RKISP1_CSI_PAD_SRC);
> 
> last argument here should be RKISP1_CSI_PAD_SINK ?
> 
> >+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
> >+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
> >+	sink_fmt->field = V4L2_FIELD_NONE;
> >+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
> >+
> >+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
> >+					     RKISP1_CSI_PAD_SINK);
> 
> last argument here should be RKISP1_CSI_PAD_SRC ?

Yes, the two are swapped, I'll fix that.

> >+	*src_fmt = *sink_fmt;
> >+
> >+	return 0;
> >+}
> >+
> >+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
> >+			      struct v4l2_subdev_state *sd_state,
> >+			      struct v4l2_subdev_format *fmt)
> >+{
> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
> >+
> >+	mutex_lock(&csi->ops_lock);
> >+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
> >+					      fmt->which);
> >+	mutex_unlock(&csi->ops_lock);
> >+	return 0;
> >+}
> >+
> >+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
> >+			      struct v4l2_subdev_state *sd_state,
> >+			      struct v4l2_subdev_format *fmt)
> >+{
> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
> >+
> >+	mutex_lock(&csi->ops_lock);
> >+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
> >+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
> >+					fmt->which);
> >+	else
> >+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
> >+				       fmt->which);
> >+
> >+	mutex_unlock(&csi->ops_lock);
> >+	return 0;
> >+}
> >+
> >+/* ----------------------------------------------------------------------------
> >+ * Subdev video operations
> >+ */
> >+
> >+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
> >+{
> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
> >+	struct rkisp1_device *rkisp1 = csi->rkisp1;
> >+	struct media_pad *source_pad;
> >+	struct v4l2_subdev *source;
> >+	int ret;
> >+
> >+	if (!enable) {
> >+		v4l2_subdev_call(csi->source->sd, video, s_stream,
> >+				 false);
> >+
> >+		rkisp1_csi_stop(csi);
> >+
> >+		return ret;
> 
> ret is uninitialized here

Fixed.
 
> >+	}
> >+
> >+	source_pad = media_entity_remote_source_pad(&sd->entity);
> >+	if (IS_ERR(source_pad)) {
> >+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);
> 
> here you should print 'ERR_PTR(source_pad)' instead of 'ret'

Indeed.

Thanks for catching all those mistakes.

> >+		return -EPIPE;
> >+	}
> >+
> >+	source = media_entity_to_v4l2_subdev(source_pad->entity);
> >+	if (!source) {
> >+		/* This should really not happen, so is not worth a message. */
> >+		return -EPIPE;
> >+	}
> >+
> >+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
> >+				   asd);
> >+
> >+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
> >+		return -EINVAL;
> >+
> >+	mutex_lock(&csi->ops_lock);
> >+	ret = rkisp1_csi_start(csi, csi->source);
> >+	mutex_unlock(&csi->ops_lock);
> >+	if (ret)
> >+		return ret;
> >+
> >+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
> >+
> >+	return 0;
> >+}
> >+
> >+/* ----------------------------------------------------------------------------
> >+ * Registration
> >+ */
> >+
> >+static const struct media_entity_operations rkisp1_csi_media_ops = {
> >+	.link_validate = v4l2_subdev_link_validate,
> >+};
> >+
> >+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
> >+	.s_stream = rkisp1_csi_s_stream,
> >+};
> >+
> >+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
> >+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
> >+	.init_cfg = rkisp1_csi_init_config,
> >+	.get_fmt = rkisp1_csi_get_fmt,
> >+	.set_fmt = rkisp1_csi_set_fmt,
> >+};
> >+
> >+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
> >+	.video = &rkisp1_csi_video_ops,
> >+	.pad = &rkisp1_csi_pad_ops,
> >+};
> >+
> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
> >+{
> >+	struct rkisp1_csi *csi = &rkisp1->csi;
> >+	struct v4l2_subdev_state state = {};
> >+	struct media_pad *pads;
> >+	struct v4l2_subdev *sd;
> >+	int ret;
> >+
> >+	csi->rkisp1 = rkisp1;
> >+	mutex_init(&csi->ops_lock);
> >+
> >+	sd = &csi->sd;
> >+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
> >+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
> >+	sd->entity.ops = &rkisp1_csi_media_ops;
> >+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
> >+	sd->owner = THIS_MODULE;
> >+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
> >+
> >+	pads = csi->pads;
> >+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
> >+					  MEDIA_PAD_FL_MUST_CONNECT;
> >+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
> >+					 MEDIA_PAD_FL_MUST_CONNECT;
> >+
> >+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
> >+	if (ret)
> >+		goto error;
> >+
> >+	state.pads = csi->pad_cfg;
> >+	rkisp1_csi_init_config(sd, &state);
> >+
> >+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
> >+	if (ret) {
> >+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
> >+		goto error;
> >+	}
> >+
> >+	return 0;
> >+
> >+error:
> >+	media_entity_cleanup(&sd->entity);
> >+	mutex_destroy(&csi->ops_lock);
> >+	csi->rkisp1 = NULL;
> >+	return ret;
> >+}
> >+
> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
> >+{
> >+	struct rkisp1_csi *csi = &rkisp1->csi;
> >+
> >+	if (!csi->rkisp1)
> >+		return;
> >+
> >+	v4l2_device_unregister_subdev(&csi->sd);
> >+	media_entity_cleanup(&csi->sd.entity);
> >+	mutex_destroy(&csi->ops_lock);
> >+}
> >+
> > int rkisp1_csi_init(struct rkisp1_device *rkisp1)
> > {
> > 	struct rkisp1_csi *csi = &rkisp1->csi;
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> >index 97ce7e7959ab..ddf8e5e08f55 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> >@@ -13,10 +13,14 @@
> >
> > struct rkisp1_device;
> > struct rkisp1_sensor_async;
> >+struct v4l2_subdev;
> >
> > int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> > void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> >
> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
> >+
> > int rkisp1_csi_start(struct rkisp1_csi *csi,
> > 		     const struct rkisp1_sensor_async *sensor);
> > void rkisp1_csi_stop(struct rkisp1_csi *csi);
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >index 253220188abd..faf2cd4c8149 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> >
> > static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
> > {
> >+	rkisp1_csi_unregister(rkisp1);
> > 	rkisp1_params_unregister(rkisp1);
> > 	rkisp1_stats_unregister(rkisp1);
> > 	rkisp1_capture_devs_unregister(rkisp1);
> >@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> > 	if (ret)
> > 		goto error;
> >
> >+	ret = rkisp1_csi_register(rkisp1);
> >+	if (ret)
> >+		goto error;
> >+
> > 	ret = rkisp1_create_links(rkisp1);
> > 	if (ret)
> > 		goto error;

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
@ 2022-06-25 11:03       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 11:03 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Sat, Jun 25, 2022 at 10:00:34AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:11, Paul Elder wrote:
> >The CSI receiver is a component separate from the ISP or the resizers.
> >It is actually optional, not all device model include a CSI receiver. On
> >some SoCs CSI-2 support can be provided through an external CSI-2
> >receiver, connected to the ISP's parallel input.
> >
> >To support those use cases, create a V4L2 subdev to model the CSI
> >receiver. It will allow the driver to handle both internal and external
> >CSI receivers the same way.
> >
> >The next commit will plumb the CSI subdev to the rest of the driver,
> >replacing direct function calls.
> >
> >Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> >Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >---
> > .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
> > .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
> > .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
> > .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
> > 4 files changed, 313 insertions(+)
> >
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >index 3c55e922346e..0ab49d1feb55 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
> > 	RKISP1_RSZ_PAD_MAX
> > };
> >
> >+/* enum for the csi receiver pads */
> >+enum rkisp1_csi_pad {
> >+	RKISP1_CSI_PAD_SINK,
> >+	RKISP1_CSI_PAD_SRC,
> >+	RKISP1_CSI_PAD_MAX
> 
> I'd call it RKISP1_CSI_PAD_NUM

OK.

> >+};
> >+
> > /* enum for the capture id */
> > enum rkisp1_stream_id {
> > 	RKISP1_MAINPATH,
> >@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
> >  * @rkisp1: pointer to the rkisp1 device
> >  * @dphy: a pointer to the phy
> >  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
> >+ * @sd: v4l2_subdev variable
> >+ * @pads: media pads
> >+ * @pad_cfg: configurations for the pads
> >+ * @ops_lock: a lock for the subdev ops
> >+ * @source: source in-use, set when starting streaming
> >  */
> > struct rkisp1_csi {
> > 	struct rkisp1_device *rkisp1;
> > 	struct phy *dphy;
> > 	bool is_dphy_errctrl_disabled;
> >+	struct v4l2_subdev sd;
> >+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
> >+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
> >+	struct mutex ops_lock; /* serialize the subdevice ops */
> >+	struct rkisp1_sensor_async *source;
> > };
> >
> > /*
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >index 425a3b014089..8182694a6fe0 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> >@@ -15,10 +15,34 @@
> > #include <linux/phy/phy-mipi-dphy.h>
> >
> > #include <media/v4l2-ctrls.h>
> >+#include <media/v4l2-fwnode.h>
> >
> > #include "rkisp1-common.h"
> > #include "rkisp1-csi.h"
> >
> >+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
> >+
> >+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
> >+
> >+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
> >+{
> >+	return container_of(sd, struct rkisp1_csi, sd);
> >+}
> >+
> >+static struct v4l2_mbus_framefmt *
> >+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
> >+		       struct v4l2_subdev_state *sd_state,
> >+		       unsigned int pad, u32 which)
> >+{
> >+	struct v4l2_subdev_state state = {
> >+		.pads = csi->pad_cfg
> >+	};
> 
> newline here

I'm surprised checkpatch didn't warn. Fixed.

> >+	if (which == V4L2_SUBDEV_FORMAT_TRY)
> >+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
> >+	else
> >+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
> >+}
> >+
> > static int rkisp1_csi_config(struct rkisp1_csi *csi,
> > 			     const struct rkisp1_sensor_async *sensor)
> > {
> >@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
> > 	return IRQ_HANDLED;
> > }
> >
> >+/* ----------------------------------------------------------------------------
> >+ * Subdev pad operations
> >+ */
> >+
> >+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
> >+				   struct v4l2_subdev_state *sd_state,
> >+				   struct v4l2_mbus_framefmt *format,
> >+				   unsigned int which)
> >+{
> >+	struct v4l2_mbus_framefmt *sink_fmt;
> >+
> >+	/* We don't set the src format directly; take it from the sink format */
> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
> >+					  which);
> >+
> >+	*format = *sink_fmt;
> >+}
> >+
> >+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
> >+				    struct v4l2_subdev_state *sd_state,
> >+				    struct v4l2_mbus_framefmt *format,
> >+				    unsigned int which)
> >+{
> >+	const struct rkisp1_mbus_info *mbus_info;
> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
> >+
> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
> >+					  which);
> >+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
> >+					 which);
> >+
> >+	sink_fmt->code = format->code;
> >+
> >+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> >+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
> >+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
> >+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
> >+	}
> >+
> >+	sink_fmt->width = clamp_t(u32, format->width,
> >+				  RKISP1_ISP_MIN_WIDTH,
> >+				  RKISP1_ISP_MAX_WIDTH);
> >+	sink_fmt->height = clamp_t(u32, format->height,
> >+				   RKISP1_ISP_MIN_HEIGHT,
> >+				   RKISP1_ISP_MAX_HEIGHT);
> >+
> >+	/* Propagate to source pad */
> >+	src_fmt->code = sink_fmt->code;
> >+	src_fmt->width = sink_fmt->width;
> >+	src_fmt->height = sink_fmt->height;
> >+
> 
> why here you don't do '*src_fmt = *sink_fmt' instead of per field propaget ?

You're right, the CSI-2 receiver doesn't change the format in any way,
that would be easier.

> >+	*format = *sink_fmt;
> >+}
> >+
> >+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
> >+				     struct v4l2_subdev_state *sd_state,
> >+				     struct v4l2_subdev_mbus_code_enum *code)
> >+{
> >+	unsigned int i;
> >+	int pos = 0;
> >+
> >+	if (code->index >= rkisp1_mbus_info_length())
> >+		return -EINVAL;
> >+
> >+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
> >+		const struct rkisp1_mbus_info *fmt =
> >+			rkisp1_mbus_info_get_by_index(i);
> >+
> >+		if (fmt->direction & RKISP1_ISP_SD_SINK)
> >+			pos++;
> >+
> >+		if (code->index == pos - 1) {
> >+			code->code = fmt->mbus_code;
> >+			return 0;
> >+		}
> >+	}
> >+
> >+	return -EINVAL;
> >+}
> >+
> >+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
> >+				  struct v4l2_subdev_state *sd_state)
> >+{
> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
> >+
> >+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
> >+					      RKISP1_CSI_PAD_SRC);
> 
> last argument here should be RKISP1_CSI_PAD_SINK ?
> 
> >+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
> >+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
> >+	sink_fmt->field = V4L2_FIELD_NONE;
> >+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
> >+
> >+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
> >+					     RKISP1_CSI_PAD_SINK);
> 
> last argument here should be RKISP1_CSI_PAD_SRC ?

Yes, the two are swapped, I'll fix that.

> >+	*src_fmt = *sink_fmt;
> >+
> >+	return 0;
> >+}
> >+
> >+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
> >+			      struct v4l2_subdev_state *sd_state,
> >+			      struct v4l2_subdev_format *fmt)
> >+{
> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
> >+
> >+	mutex_lock(&csi->ops_lock);
> >+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
> >+					      fmt->which);
> >+	mutex_unlock(&csi->ops_lock);
> >+	return 0;
> >+}
> >+
> >+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
> >+			      struct v4l2_subdev_state *sd_state,
> >+			      struct v4l2_subdev_format *fmt)
> >+{
> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
> >+
> >+	mutex_lock(&csi->ops_lock);
> >+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
> >+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
> >+					fmt->which);
> >+	else
> >+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
> >+				       fmt->which);
> >+
> >+	mutex_unlock(&csi->ops_lock);
> >+	return 0;
> >+}
> >+
> >+/* ----------------------------------------------------------------------------
> >+ * Subdev video operations
> >+ */
> >+
> >+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
> >+{
> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
> >+	struct rkisp1_device *rkisp1 = csi->rkisp1;
> >+	struct media_pad *source_pad;
> >+	struct v4l2_subdev *source;
> >+	int ret;
> >+
> >+	if (!enable) {
> >+		v4l2_subdev_call(csi->source->sd, video, s_stream,
> >+				 false);
> >+
> >+		rkisp1_csi_stop(csi);
> >+
> >+		return ret;
> 
> ret is uninitialized here

Fixed.
 
> >+	}
> >+
> >+	source_pad = media_entity_remote_source_pad(&sd->entity);
> >+	if (IS_ERR(source_pad)) {
> >+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);
> 
> here you should print 'ERR_PTR(source_pad)' instead of 'ret'

Indeed.

Thanks for catching all those mistakes.

> >+		return -EPIPE;
> >+	}
> >+
> >+	source = media_entity_to_v4l2_subdev(source_pad->entity);
> >+	if (!source) {
> >+		/* This should really not happen, so is not worth a message. */
> >+		return -EPIPE;
> >+	}
> >+
> >+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
> >+				   asd);
> >+
> >+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
> >+		return -EINVAL;
> >+
> >+	mutex_lock(&csi->ops_lock);
> >+	ret = rkisp1_csi_start(csi, csi->source);
> >+	mutex_unlock(&csi->ops_lock);
> >+	if (ret)
> >+		return ret;
> >+
> >+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
> >+
> >+	return 0;
> >+}
> >+
> >+/* ----------------------------------------------------------------------------
> >+ * Registration
> >+ */
> >+
> >+static const struct media_entity_operations rkisp1_csi_media_ops = {
> >+	.link_validate = v4l2_subdev_link_validate,
> >+};
> >+
> >+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
> >+	.s_stream = rkisp1_csi_s_stream,
> >+};
> >+
> >+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
> >+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
> >+	.init_cfg = rkisp1_csi_init_config,
> >+	.get_fmt = rkisp1_csi_get_fmt,
> >+	.set_fmt = rkisp1_csi_set_fmt,
> >+};
> >+
> >+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
> >+	.video = &rkisp1_csi_video_ops,
> >+	.pad = &rkisp1_csi_pad_ops,
> >+};
> >+
> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
> >+{
> >+	struct rkisp1_csi *csi = &rkisp1->csi;
> >+	struct v4l2_subdev_state state = {};
> >+	struct media_pad *pads;
> >+	struct v4l2_subdev *sd;
> >+	int ret;
> >+
> >+	csi->rkisp1 = rkisp1;
> >+	mutex_init(&csi->ops_lock);
> >+
> >+	sd = &csi->sd;
> >+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
> >+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
> >+	sd->entity.ops = &rkisp1_csi_media_ops;
> >+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
> >+	sd->owner = THIS_MODULE;
> >+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
> >+
> >+	pads = csi->pads;
> >+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
> >+					  MEDIA_PAD_FL_MUST_CONNECT;
> >+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
> >+					 MEDIA_PAD_FL_MUST_CONNECT;
> >+
> >+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
> >+	if (ret)
> >+		goto error;
> >+
> >+	state.pads = csi->pad_cfg;
> >+	rkisp1_csi_init_config(sd, &state);
> >+
> >+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
> >+	if (ret) {
> >+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
> >+		goto error;
> >+	}
> >+
> >+	return 0;
> >+
> >+error:
> >+	media_entity_cleanup(&sd->entity);
> >+	mutex_destroy(&csi->ops_lock);
> >+	csi->rkisp1 = NULL;
> >+	return ret;
> >+}
> >+
> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
> >+{
> >+	struct rkisp1_csi *csi = &rkisp1->csi;
> >+
> >+	if (!csi->rkisp1)
> >+		return;
> >+
> >+	v4l2_device_unregister_subdev(&csi->sd);
> >+	media_entity_cleanup(&csi->sd.entity);
> >+	mutex_destroy(&csi->ops_lock);
> >+}
> >+
> > int rkisp1_csi_init(struct rkisp1_device *rkisp1)
> > {
> > 	struct rkisp1_csi *csi = &rkisp1->csi;
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> >index 97ce7e7959ab..ddf8e5e08f55 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> >@@ -13,10 +13,14 @@
> >
> > struct rkisp1_device;
> > struct rkisp1_sensor_async;
> >+struct v4l2_subdev;
> >
> > int rkisp1_csi_init(struct rkisp1_device *rkisp1);
> > void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> >
> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
> >+
> > int rkisp1_csi_start(struct rkisp1_csi *csi,
> > 		     const struct rkisp1_sensor_async *sensor);
> > void rkisp1_csi_stop(struct rkisp1_csi *csi);
> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >index 253220188abd..faf2cd4c8149 100644
> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> >
> > static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
> > {
> >+	rkisp1_csi_unregister(rkisp1);
> > 	rkisp1_params_unregister(rkisp1);
> > 	rkisp1_stats_unregister(rkisp1);
> > 	rkisp1_capture_devs_unregister(rkisp1);
> >@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> > 	if (ret)
> > 		goto error;
> >
> >+	ret = rkisp1_csi_register(rkisp1);
> >+	if (ret)
> >+		goto error;
> >+
> > 	ret = rkisp1_create_links(rkisp1);
> > 	if (ret)
> > 		goto error;

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
  2022-06-25  7:45     ` Dafna Hirschfeld
@ 2022-06-25 16:07       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 16:07 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Sat, Jun 25, 2022 at 10:45:59AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:11, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > Connect the CSI receiver subdevice into the rest of the driver. This
> > includes:
> 
> To make it clear where you put the csi, i'll add here
> 'Connect the CSI subdevice between the source
> and the isp' or something like that.
> 
> Also the sketch 'Media Topology' in rkisp1-dev.c should be updated.

Good point, I'll do that.

> I'd also wonder if we should ignore src configuration of the isp entity
> since it must be identical to the sink of the csi.

What do you mean exactly by ignoring it ?

> > - calling the subdevice via the v4l2 subdev API
> > - moving the async notifier for the sensor from the ISP to the CSI
> >   receiver
> > - in the ISP, create a media link to the CSI receiver, and remove the
> >   media link creation to the sensor
> > - in the CSI receiver, create a media link to the sensor
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
> >  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
> >  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
> >  4 files changed, 53 insertions(+), 44 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > index 8182694a6fe0..96712b467dde 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > @@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
> >  		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
> >  }
> > 
> > +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> > +			   struct rkisp1_sensor_async *s_asd,
> > +			   unsigned int source_pad)
> > +{
> > +	struct rkisp1_csi *csi = &rkisp1->csi;
> > +	int ret;		
> 
> extra space after 'ret;' ?

Oh.

Paul, did you get so used to the fact that checkstyle.py is integrated
in git hooks in libcamera that you forgot that checkpatch.pl has to be
run manually ? :-)

> > +
> > +	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> > +						V4L2_CID_PIXEL_RATE);
> > +	if (!s_asd->pixel_rate_ctrl) {
> > +		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> > +			sd->name);
> > +		return -EINVAL;
> > +	}
> > +
> > +	/* Create the link from the sensor to the CSI receiver. */
> > +	ret = media_create_pad_link(&sd->entity, source_pad,
> > +				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
> > +				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> > +	if (ret) {
> > +		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
> > +			sd->name);
> > +		return ret;
> > +	}
> > +
> > +	return 0;
> > +}
> > +
> >  static int rkisp1_csi_config(struct rkisp1_csi *csi,
> >  			     const struct rkisp1_sensor_async *sensor)
> >  {
> > @@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> >  		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> >  }
> > 
> > -int rkisp1_csi_start(struct rkisp1_csi *csi,
> > -		     const struct rkisp1_sensor_async *sensor)
> > +static int rkisp1_csi_start(struct rkisp1_csi *csi,
> > +			    const struct rkisp1_sensor_async *sensor)
> >  {
> >  	struct rkisp1_device *rkisp1 = csi->rkisp1;
> >  	union phy_configure_opts opts;
> > @@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
> >  	return 0;
> >  }
> > 
> > -void rkisp1_csi_stop(struct rkisp1_csi *csi)
> > +static void rkisp1_csi_stop(struct rkisp1_csi *csi)
> >  {
> >  	rkisp1_csi_disable(csi);
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > index ddf8e5e08f55..eadcd24f65fb 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > @@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> >  int rkisp1_csi_register(struct rkisp1_device *rkisp1);
> >  void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
> > 
> > -int rkisp1_csi_start(struct rkisp1_csi *csi,
> > -		     const struct rkisp1_sensor_async *sensor);
> > -void rkisp1_csi_stop(struct rkisp1_csi *csi);
> > +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> > +			   struct rkisp1_sensor_async *s_asd,
> > +			   unsigned int source_pad);
> > 
> >  #endif /* _RKISP1_CSI_H */
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index faf2cd4c8149..a3e182c86bdd 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -17,6 +17,7 @@
> >  #include <linux/pinctrl/consumer.h>
> >  #include <linux/pm_runtime.h>
> >  #include <media/v4l2-fwnode.h>
> > +#include <media/v4l2-mc.h>
> > 
> >  #include "rkisp1-common.h"
> >  #include "rkisp1-csi.h"
> > @@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  		container_of(asd, struct rkisp1_sensor_async, asd);
> >  	int source_pad;
> > 
> > -	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> > -						V4L2_CID_PIXEL_RATE);
> > -	if (!s_asd->pixel_rate_ctrl) {
> > -		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> > -			sd->name);
> > -		return -EINVAL;
> > -	}
> > -
> >  	s_asd->sd = sd;
> > 
> > -	/* Create the link to the sensor. */
> >  	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> >  						 MEDIA_PAD_FL_SOURCE);
> >  	if (source_pad < 0) {
> > @@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  		return source_pad;
> >  	}
> > 
> > -	return media_create_pad_link(&sd->entity, source_pad,
> > -				     &rkisp1->isp.sd.entity,
> > -				     RKISP1_ISP_PAD_SINK_VIDEO,
> > -				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> > +	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
> >  }
> > 
> >  static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> > @@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> >  	unsigned int i;
> >  	int ret;
> > 
> > +	/* Link the CSI receiver to the ISP. */
> > +	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
> > +				    &rkisp1->isp.sd.entity,
> > +				    RKISP1_ISP_PAD_SINK_VIDEO,
> > +				    MEDIA_LNK_FL_ENABLED);
> 
> should this also be immutable?

I don't think so, because one could connect a parallel sensor directly
to the ISP parallel input. This isn't well supported in the driver today
though, probably because nobody has cared much about upstreaming support
for such a setup, but I think it's a valid hardware option.

> > +	if (ret)
> > +		return ret;
> > +
> >  	/* create ISP->RSZ->CAP links */
> >  	for (i = 0; i < 2; i++) {
> >  		struct media_entity *resizer =
> > @@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> >  	if (ret)
> >  		goto error;
> > 
> > -	ret = rkisp1_subdev_notifier_register(rkisp1);
> > -	if (ret) {
> > -		dev_err(rkisp1->dev,
> > -			"Failed to register subdev notifier(%d)\n", ret);
> > -		goto error;
> > -	}
> > -
> >  	return 0;
> > 
> >  error:
> > @@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
> >  	if (ret)
> >  		goto err_cleanup_csi;
> > 
> > +	ret = rkisp1_subdev_notifier_register(rkisp1);
> > +	if (ret)
> > +		goto err_unreg_entities;
> > +
> >  	rkisp1_debug_init(rkisp1);
> > 
> >  	return 0;
> > 
> > +err_unreg_entities:
> > +	rkisp1_entities_unregister(rkisp1);
> >  err_cleanup_csi:
> >  	rkisp1_csi_cleanup(rkisp1);
> >  err_unreg_media_dev:
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > index 5afb8be311c7..260c9ce0dca4 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > @@ -16,7 +16,6 @@
> >  #include <media/v4l2-event.h>
> > 
> >  #include "rkisp1-common.h"
> > -#include "rkisp1-csi.h"
> > 
> >  #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> >  #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
> > @@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  {
> >  	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> >  	struct rkisp1_device *rkisp1 = isp->rkisp1;
> > -	const struct rkisp1_sensor_async *asd;
> >  	struct media_pad *source_pad;
> >  	int ret;
> > 
> >  	if (!enable) {
> >  		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
> > -
> > -		rkisp1_csi_stop(&rkisp1->csi);
> >  		rkisp1_isp_stop(isp);
> > -
> >  		return 0;
> >  	}
> > 
> > @@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  		return -EPIPE;
> >  	}
> > 
> > -	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
> > -			   asd);
> > -
> > -	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> > -		return -EINVAL;
> > +	if (rkisp1->source != &rkisp1->csi.sd)
> > +		return -EPIPE;
> 
> This is not very clear, 'source' should point to the remote source (the one outside this driver)
> so why should it be 'csi.sd' ?
> Or is it that now 'rkips1->source' might be either the remote source or csi? if so I think it is a bit confusing.

rkisp1->source is the source of the ISP. it can be the CSI-2 receiver,
or if a parallel sensor is connected directly to the ISP, the sensor
itself. The check here is meant to catch bugs in the implementation
while transitioning, as in this patch external CSI-2 receivers or
parallel sensors are not supported yet. Patch "media: rkisp1: Support
the ISP parallel input" then changes this code.

> > 
> >  	isp->frame_sequence = -1;
> >  	mutex_lock(&isp->ops_lock);
> > -	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
> > +	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
> >  	if (ret)
> >  		goto mutex_unlock;
> > 
> >  	rkisp1_isp_start(isp);
> > 
> > -	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> > -	if (ret) {
> > -		rkisp1_isp_stop(isp);
> > -		goto mutex_unlock;
> > -	}
> > -
> >  	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 
> Now that isp should call 's_stream' for 'rkisp1->csi->sd' and not 'rkisp1->source'.

As explained above, I think source is correct here, as rkisp1->csi is
the internal CSI-2 receiver, which may or may not be the source of the
ISP, depending on link configuration.

> >  	if (ret) {
> >  		rkisp1_isp_stop(isp);
> > -		rkisp1_csi_stop(&rkisp1->csi);
> >  		goto mutex_unlock;
> >  	}
> > 

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev
@ 2022-06-25 16:07       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 16:07 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Sat, Jun 25, 2022 at 10:45:59AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:11, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > Connect the CSI receiver subdevice into the rest of the driver. This
> > includes:
> 
> To make it clear where you put the csi, i'll add here
> 'Connect the CSI subdevice between the source
> and the isp' or something like that.
> 
> Also the sketch 'Media Topology' in rkisp1-dev.c should be updated.

Good point, I'll do that.

> I'd also wonder if we should ignore src configuration of the isp entity
> since it must be identical to the sink of the csi.

What do you mean exactly by ignoring it ?

> > - calling the subdevice via the v4l2 subdev API
> > - moving the async notifier for the sensor from the ISP to the CSI
> >   receiver
> > - in the ISP, create a media link to the CSI receiver, and remove the
> >   media link creation to the sensor
> > - in the CSI receiver, create a media link to the sensor
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-csi.c     | 34 ++++++++++++++++--
> >  .../platform/rockchip/rkisp1/rkisp1-csi.h     |  6 ++--
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 36 +++++++++----------
> >  .../platform/rockchip/rkisp1/rkisp1-isp.c     | 21 ++---------
> >  4 files changed, 53 insertions(+), 44 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > index 8182694a6fe0..96712b467dde 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
> > @@ -43,6 +43,34 @@ rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
> >  		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
> >  }
> > 
> > +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> > +			   struct rkisp1_sensor_async *s_asd,
> > +			   unsigned int source_pad)
> > +{
> > +	struct rkisp1_csi *csi = &rkisp1->csi;
> > +	int ret;		
> 
> extra space after 'ret;' ?

Oh.

Paul, did you get so used to the fact that checkstyle.py is integrated
in git hooks in libcamera that you forgot that checkpatch.pl has to be
run manually ? :-)

> > +
> > +	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> > +						V4L2_CID_PIXEL_RATE);
> > +	if (!s_asd->pixel_rate_ctrl) {
> > +		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> > +			sd->name);
> > +		return -EINVAL;
> > +	}
> > +
> > +	/* Create the link from the sensor to the CSI receiver. */
> > +	ret = media_create_pad_link(&sd->entity, source_pad,
> > +				    &csi->sd.entity, RKISP1_CSI_PAD_SINK,
> > +				    !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> > +	if (ret) {
> > +		dev_err(csi->rkisp1->dev, "failed to link src pad of %s\n",
> > +			sd->name);
> > +		return ret;
> > +	}
> > +
> > +	return 0;
> > +}
> > +
> >  static int rkisp1_csi_config(struct rkisp1_csi *csi,
> >  			     const struct rkisp1_sensor_async *sensor)
> >  {
> > @@ -118,8 +146,8 @@ static void rkisp1_csi_disable(struct rkisp1_csi *csi)
> >  		     val & (~RKISP1_CIF_MIPI_CTRL_OUTPUT_ENA));
> >  }
> > 
> > -int rkisp1_csi_start(struct rkisp1_csi *csi,
> > -		     const struct rkisp1_sensor_async *sensor)
> > +static int rkisp1_csi_start(struct rkisp1_csi *csi,
> > +			    const struct rkisp1_sensor_async *sensor)
> >  {
> >  	struct rkisp1_device *rkisp1 = csi->rkisp1;
> >  	union phy_configure_opts opts;
> > @@ -155,7 +183,7 @@ int rkisp1_csi_start(struct rkisp1_csi *csi,
> >  	return 0;
> >  }
> > 
> > -void rkisp1_csi_stop(struct rkisp1_csi *csi)
> > +static void rkisp1_csi_stop(struct rkisp1_csi *csi)
> >  {
> >  	rkisp1_csi_disable(csi);
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > index ddf8e5e08f55..eadcd24f65fb 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
> > @@ -21,8 +21,8 @@ void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
> >  int rkisp1_csi_register(struct rkisp1_device *rkisp1);
> >  void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
> > 
> > -int rkisp1_csi_start(struct rkisp1_csi *csi,
> > -		     const struct rkisp1_sensor_async *sensor);
> > -void rkisp1_csi_stop(struct rkisp1_csi *csi);
> > +int rkisp1_csi_link_sensor(struct rkisp1_device *rkisp1, struct v4l2_subdev *sd,
> > +			   struct rkisp1_sensor_async *s_asd,
> > +			   unsigned int source_pad);
> > 
> >  #endif /* _RKISP1_CSI_H */
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index faf2cd4c8149..a3e182c86bdd 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -17,6 +17,7 @@
> >  #include <linux/pinctrl/consumer.h>
> >  #include <linux/pm_runtime.h>
> >  #include <media/v4l2-fwnode.h>
> > +#include <media/v4l2-mc.h>
> > 
> >  #include "rkisp1-common.h"
> >  #include "rkisp1-csi.h"
> > @@ -119,17 +120,8 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  		container_of(asd, struct rkisp1_sensor_async, asd);
> >  	int source_pad;
> > 
> > -	s_asd->pixel_rate_ctrl = v4l2_ctrl_find(sd->ctrl_handler,
> > -						V4L2_CID_PIXEL_RATE);
> > -	if (!s_asd->pixel_rate_ctrl) {
> > -		dev_err(rkisp1->dev, "No pixel rate control in subdev %s\n",
> > -			sd->name);
> > -		return -EINVAL;
> > -	}
> > -
> >  	s_asd->sd = sd;
> > 
> > -	/* Create the link to the sensor. */
> >  	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> >  						 MEDIA_PAD_FL_SOURCE);
> >  	if (source_pad < 0) {
> > @@ -138,10 +130,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  		return source_pad;
> >  	}
> > 
> > -	return media_create_pad_link(&sd->entity, source_pad,
> > -				     &rkisp1->isp.sd.entity,
> > -				     RKISP1_ISP_PAD_SINK_VIDEO,
> > -				     !s_asd->index ? MEDIA_LNK_FL_ENABLED : 0);
> > +	return rkisp1_csi_link_sensor(rkisp1, sd, s_asd, source_pad);
> >  }
> > 
> >  static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> > @@ -283,6 +272,14 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
> >  	unsigned int i;
> >  	int ret;
> > 
> > +	/* Link the CSI receiver to the ISP. */
> > +	ret = media_create_pad_link(&rkisp1->csi.sd.entity, RKISP1_CSI_PAD_SRC,
> > +				    &rkisp1->isp.sd.entity,
> > +				    RKISP1_ISP_PAD_SINK_VIDEO,
> > +				    MEDIA_LNK_FL_ENABLED);
> 
> should this also be immutable?

I don't think so, because one could connect a parallel sensor directly
to the ISP parallel input. This isn't well supported in the driver today
though, probably because nobody has cared much about upstreaming support
for such a setup, but I think it's a valid hardware option.

> > +	if (ret)
> > +		return ret;
> > +
> >  	/* create ISP->RSZ->CAP links */
> >  	for (i = 0; i < 2; i++) {
> >  		struct media_entity *resizer =
> > @@ -364,13 +361,6 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
> >  	if (ret)
> >  		goto error;
> > 
> > -	ret = rkisp1_subdev_notifier_register(rkisp1);
> > -	if (ret) {
> > -		dev_err(rkisp1->dev,
> > -			"Failed to register subdev notifier(%d)\n", ret);
> > -		goto error;
> > -	}
> > -
> >  	return 0;
> > 
> >  error:
> > @@ -534,10 +524,16 @@ static int rkisp1_probe(struct platform_device *pdev)
> >  	if (ret)
> >  		goto err_cleanup_csi;
> > 
> > +	ret = rkisp1_subdev_notifier_register(rkisp1);
> > +	if (ret)
> > +		goto err_unreg_entities;
> > +
> >  	rkisp1_debug_init(rkisp1);
> > 
> >  	return 0;
> > 
> > +err_unreg_entities:
> > +	rkisp1_entities_unregister(rkisp1);
> >  err_cleanup_csi:
> >  	rkisp1_csi_cleanup(rkisp1);
> >  err_unreg_media_dev:
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > index 5afb8be311c7..260c9ce0dca4 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
> > @@ -16,7 +16,6 @@
> >  #include <media/v4l2-event.h>
> > 
> >  #include "rkisp1-common.h"
> > -#include "rkisp1-csi.h"
> > 
> >  #define RKISP1_DEF_SINK_PAD_FMT MEDIA_BUS_FMT_SRGGB10_1X10
> >  #define RKISP1_DEF_SRC_PAD_FMT MEDIA_BUS_FMT_YUYV8_2X8
> > @@ -728,16 +727,12 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  {
> >  	struct rkisp1_isp *isp = to_rkisp1_isp(sd);
> >  	struct rkisp1_device *rkisp1 = isp->rkisp1;
> > -	const struct rkisp1_sensor_async *asd;
> >  	struct media_pad *source_pad;
> >  	int ret;
> > 
> >  	if (!enable) {
> >  		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
> > -
> > -		rkisp1_csi_stop(&rkisp1->csi);
> >  		rkisp1_isp_stop(isp);
> > -
> >  		return 0;
> >  	}
> > 
> > @@ -754,30 +749,20 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> >  		return -EPIPE;
> >  	}
> > 
> > -	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
> > -			   asd);
> > -
> > -	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> > -		return -EINVAL;
> > +	if (rkisp1->source != &rkisp1->csi.sd)
> > +		return -EPIPE;
> 
> This is not very clear, 'source' should point to the remote source (the one outside this driver)
> so why should it be 'csi.sd' ?
> Or is it that now 'rkips1->source' might be either the remote source or csi? if so I think it is a bit confusing.

rkisp1->source is the source of the ISP. it can be the CSI-2 receiver,
or if a parallel sensor is connected directly to the ISP, the sensor
itself. The check here is meant to catch bugs in the implementation
while transitioning, as in this patch external CSI-2 receivers or
parallel sensors are not supported yet. Patch "media: rkisp1: Support
the ISP parallel input" then changes this code.

> > 
> >  	isp->frame_sequence = -1;
> >  	mutex_lock(&isp->ops_lock);
> > -	ret = rkisp1_config_cif(isp, asd->mbus_type, asd->mbus_flags);
> > +	ret = rkisp1_config_cif(isp, V4L2_MBUS_CSI2_DPHY, 0);
> >  	if (ret)
> >  		goto mutex_unlock;
> > 
> >  	rkisp1_isp_start(isp);
> > 
> > -	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> > -	if (ret) {
> > -		rkisp1_isp_stop(isp);
> > -		goto mutex_unlock;
> > -	}
> > -
> >  	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 
> Now that isp should call 's_stream' for 'rkisp1->csi->sd' and not 'rkisp1->source'.

As explained above, I think source is correct here, as rkisp1->csi is
the internal CSI-2 receiver, which may or may not be the source of the
ISP, depending on link configuration.

> >  	if (ret) {
> >  		rkisp1_isp_stop(isp);
> > -		rkisp1_csi_stop(&rkisp1->csi);
> >  		goto mutex_unlock;
> >  	}
> > 

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-17 11:48     ` Hans Verkuil
@ 2022-06-25 17:00       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:00 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
> On 6/14/22 21:11, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > The media_entity_remote_pad() helper function returns the first remote
> > pad it find connected to a given pad. Beside being possibly ill-named
> > (as it operates on a pad, not an entity) and non-deterministic (as it
> > stops at the first enabled link), the fact that it returns the first
> > match makes it unsuitable for drivers that need to guarantee that a
> > single link is enabled, for instance when an entity can process data
> > from one of multiple sources at a time.
> 
> Question: of all the callers of this function, are there any that really
> need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
> 
> Would it be possible to replace all callers of the old function with the
> new function? If that's the case, then the _unique suffix can be dropped,
> since that would effectively be the default. And if a function is needed
> to handle the case where there are multiple enabled links, then a new
> function should be created.

I don't think so. media_entity_remote_pad() operates on a pad, switching
to media_pad_remote_pad_unique() wouldn't work on subdevs that have
multiple sink or source pads with one active link each.

> Also, media_entity_remote_pad() should really be renamed to
> media_pad_remote_pad_first() or something like that, right? I'm not saying
> you should, but that's really what it does, as I understand it.

Yes, I think that would make sense, and it would freethe
media_entity_remote_pad() name, so the new function wouldn't need the
_unique suffix. I'll give it a try.

> > For those use cases, add a new helper function,
> > media_entity_remote_pad_unique(), that operates on an entity and returns
> > a remote pad, with a guarantee that only one link is enabled. To ease
> > its use in drivers, also add an inline wrapper that locates source pads
> > specifically. A wrapper that locates sink pads can easily be added when
> > needed.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  Documentation/driver-api/media/mc-core.rst |  4 +-
> >  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >  3 files changed, 85 insertions(+), 2 deletions(-)
> > 
> > diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> > index 02481a2513b9..a2d1e32e3abb 100644
> > --- a/Documentation/driver-api/media/mc-core.rst
> > +++ b/Documentation/driver-api/media/mc-core.rst
> > @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >  
> >  Helper functions can be used to find a link between two given pads, or a pad
> >  connected to another pad through an enabled link
> > -:c:func:`media_entity_find_link()` and
> > -:c:func:`media_entity_remote_pad()`.
> > +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> > +:c:func:`media_entity_remote_source_pad()`).
> >  
> >  Use count and power handling
> >  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> > diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> > index 11f5207f73aa..1febf5a86be6 100644
> > --- a/drivers/media/mc/mc-entity.c
> > +++ b/drivers/media/mc/mc-entity.c
> > @@ -9,6 +9,7 @@
> >   */
> >  
> >  #include <linux/bitmap.h>
> > +#include <linux/list.h>
> >  #include <linux/property.h>
> >  #include <linux/slab.h>
> >  #include <media/media-entity.h>
> > @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >  }
> >  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >  
> > +struct media_pad *
> > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > +			       unsigned int type)
> > +{
> > +	struct media_pad *pad = NULL;
> > +	struct media_link *link;
> > +
> > +	list_for_each_entry(link, &entity->links, list) {
> > +		struct media_pad *local_pad;
> > +		struct media_pad *remote_pad;
> > +
> > +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> > +			continue;
> > +
> > +		if (type == MEDIA_PAD_FL_SOURCE) {
> > +			local_pad = link->sink;
> > +			remote_pad = link->source;
> > +		} else {
> > +			local_pad = link->source;
> > +			remote_pad = link->sink;
> > +		}
> > +
> > +		if (local_pad->entity == entity) {
> > +			if (pad)
> > +				return ERR_PTR(-ENOTUNIQ);
> > +
> > +			pad = remote_pad;
> > +		}
> > +	}
> > +
> > +	if (!pad)
> > +		return ERR_PTR(-ENOLINK);
> > +
> > +	return pad;
> > +}
> > +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> > +
> >  static void media_interface_init(struct media_device *mdev,
> >  				 struct media_interface *intf,
> >  				 u32 gobj_type,
> > diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> > index a9a1c0ec5d1c..33d5f52719a0 100644
> > --- a/include/media/media-entity.h
> > +++ b/include/media/media-entity.h
> > @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >   */
> >  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >  
> > +/**
> > + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> > + * @entity: The entity
> > + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> > + *
> > + * Search for and return a remote pad of @type connected to @entity through an
> > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > + * is returned.
> > + *
> > + * The uniqueness constraint makes this helper function suitable for entities
> > + * that support a single active source or sink at a time.
> > + *
> > + * Return: A pointer to the remote pad, or one of the following error pointers
> > + * if an error occurs:
> > + *
> > + * * -ENOTUNIQ - Multiple links are enabled
> > + * * -ENOLINK - No connected pad found
> > + */
> > +struct media_pad *
> > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > +			       unsigned int type);
> > +
> > +/**
> > + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> > + * @entity: The entity
> > + *
> > + * Search for and return a remote source pad connected to @entity through an
> > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > + * is returned.
> > + *
> > + * The uniqueness constraint makes this helper function suitable for entities
> > + * that support a single active source at a time.
> > + *
> > + * Return: A pointer to the remote pad, or one of the following error pointers
> > + * if an error occurs:
> > + *
> > + * * -ENOTUNIQ - Multiple links are enabled
> > + * * -ENOLINK - No connected pad found
> > + */
> > +static inline struct media_pad *
> > +media_entity_remote_source_pad(const struct media_entity *entity)
> > +{
> > +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> > +}
> > +
> >  /**
> >   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >   * @entity: The entity

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-25 17:00       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:00 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
> On 6/14/22 21:11, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > The media_entity_remote_pad() helper function returns the first remote
> > pad it find connected to a given pad. Beside being possibly ill-named
> > (as it operates on a pad, not an entity) and non-deterministic (as it
> > stops at the first enabled link), the fact that it returns the first
> > match makes it unsuitable for drivers that need to guarantee that a
> > single link is enabled, for instance when an entity can process data
> > from one of multiple sources at a time.
> 
> Question: of all the callers of this function, are there any that really
> need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
> 
> Would it be possible to replace all callers of the old function with the
> new function? If that's the case, then the _unique suffix can be dropped,
> since that would effectively be the default. And if a function is needed
> to handle the case where there are multiple enabled links, then a new
> function should be created.

I don't think so. media_entity_remote_pad() operates on a pad, switching
to media_pad_remote_pad_unique() wouldn't work on subdevs that have
multiple sink or source pads with one active link each.

> Also, media_entity_remote_pad() should really be renamed to
> media_pad_remote_pad_first() or something like that, right? I'm not saying
> you should, but that's really what it does, as I understand it.

Yes, I think that would make sense, and it would freethe
media_entity_remote_pad() name, so the new function wouldn't need the
_unique suffix. I'll give it a try.

> > For those use cases, add a new helper function,
> > media_entity_remote_pad_unique(), that operates on an entity and returns
> > a remote pad, with a guarantee that only one link is enabled. To ease
> > its use in drivers, also add an inline wrapper that locates source pads
> > specifically. A wrapper that locates sink pads can easily be added when
> > needed.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  Documentation/driver-api/media/mc-core.rst |  4 +-
> >  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >  3 files changed, 85 insertions(+), 2 deletions(-)
> > 
> > diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> > index 02481a2513b9..a2d1e32e3abb 100644
> > --- a/Documentation/driver-api/media/mc-core.rst
> > +++ b/Documentation/driver-api/media/mc-core.rst
> > @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >  
> >  Helper functions can be used to find a link between two given pads, or a pad
> >  connected to another pad through an enabled link
> > -:c:func:`media_entity_find_link()` and
> > -:c:func:`media_entity_remote_pad()`.
> > +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> > +:c:func:`media_entity_remote_source_pad()`).
> >  
> >  Use count and power handling
> >  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> > diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> > index 11f5207f73aa..1febf5a86be6 100644
> > --- a/drivers/media/mc/mc-entity.c
> > +++ b/drivers/media/mc/mc-entity.c
> > @@ -9,6 +9,7 @@
> >   */
> >  
> >  #include <linux/bitmap.h>
> > +#include <linux/list.h>
> >  #include <linux/property.h>
> >  #include <linux/slab.h>
> >  #include <media/media-entity.h>
> > @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >  }
> >  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >  
> > +struct media_pad *
> > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > +			       unsigned int type)
> > +{
> > +	struct media_pad *pad = NULL;
> > +	struct media_link *link;
> > +
> > +	list_for_each_entry(link, &entity->links, list) {
> > +		struct media_pad *local_pad;
> > +		struct media_pad *remote_pad;
> > +
> > +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> > +			continue;
> > +
> > +		if (type == MEDIA_PAD_FL_SOURCE) {
> > +			local_pad = link->sink;
> > +			remote_pad = link->source;
> > +		} else {
> > +			local_pad = link->source;
> > +			remote_pad = link->sink;
> > +		}
> > +
> > +		if (local_pad->entity == entity) {
> > +			if (pad)
> > +				return ERR_PTR(-ENOTUNIQ);
> > +
> > +			pad = remote_pad;
> > +		}
> > +	}
> > +
> > +	if (!pad)
> > +		return ERR_PTR(-ENOLINK);
> > +
> > +	return pad;
> > +}
> > +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> > +
> >  static void media_interface_init(struct media_device *mdev,
> >  				 struct media_interface *intf,
> >  				 u32 gobj_type,
> > diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> > index a9a1c0ec5d1c..33d5f52719a0 100644
> > --- a/include/media/media-entity.h
> > +++ b/include/media/media-entity.h
> > @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >   */
> >  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >  
> > +/**
> > + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> > + * @entity: The entity
> > + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> > + *
> > + * Search for and return a remote pad of @type connected to @entity through an
> > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > + * is returned.
> > + *
> > + * The uniqueness constraint makes this helper function suitable for entities
> > + * that support a single active source or sink at a time.
> > + *
> > + * Return: A pointer to the remote pad, or one of the following error pointers
> > + * if an error occurs:
> > + *
> > + * * -ENOTUNIQ - Multiple links are enabled
> > + * * -ENOLINK - No connected pad found
> > + */
> > +struct media_pad *
> > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > +			       unsigned int type);
> > +
> > +/**
> > + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> > + * @entity: The entity
> > + *
> > + * Search for and return a remote source pad connected to @entity through an
> > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > + * is returned.
> > + *
> > + * The uniqueness constraint makes this helper function suitable for entities
> > + * that support a single active source at a time.
> > + *
> > + * Return: A pointer to the remote pad, or one of the following error pointers
> > + * if an error occurs:
> > + *
> > + * * -ENOTUNIQ - Multiple links are enabled
> > + * * -ENOLINK - No connected pad found
> > + */
> > +static inline struct media_pad *
> > +media_entity_remote_source_pad(const struct media_entity *entity)
> > +{
> > +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> > +}
> > +
> >  /**
> >   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >   * @entity: The entity

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-25 17:00       ` Laurent Pinchart
@ 2022-06-25 17:28         ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:28 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Sat, Jun 25, 2022 at 08:00:51PM +0300, Laurent Pinchart wrote:
> On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
> > On 6/14/22 21:11, Paul Elder wrote:
> > > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > 
> > > The media_entity_remote_pad() helper function returns the first remote
> > > pad it find connected to a given pad. Beside being possibly ill-named
> > > (as it operates on a pad, not an entity) and non-deterministic (as it
> > > stops at the first enabled link), the fact that it returns the first
> > > match makes it unsuitable for drivers that need to guarantee that a
> > > single link is enabled, for instance when an entity can process data
> > > from one of multiple sources at a time.
> > 
> > Question: of all the callers of this function, are there any that really
> > need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
> > 
> > Would it be possible to replace all callers of the old function with the
> > new function? If that's the case, then the _unique suffix can be dropped,
> > since that would effectively be the default. And if a function is needed
> > to handle the case where there are multiple enabled links, then a new
> > function should be created.
> 
> I don't think so. media_entity_remote_pad() operates on a pad, switching
> to media_pad_remote_pad_unique() wouldn't work on subdevs that have
> multiple sink or source pads with one active link each.
> 
> > Also, media_entity_remote_pad() should really be renamed to
> > media_pad_remote_pad_first() or something like that, right? I'm not saying
> > you should, but that's really what it does, as I understand it.
> 
> Yes, I think that would make sense, and it would freethe
> media_entity_remote_pad() name, so the new function wouldn't need the
> _unique suffix. I'll give it a try.

The rename was easy enough, but I've decided to keep the
media_entity_remote_pad_unique() name and renamed
media_entity_remote_source_pad() to
media_entity_remote_source_pad_unique() to make the API clearer. If
those names end up being too long, we can rename them later.

> > > For those use cases, add a new helper function,
> > > media_entity_remote_pad_unique(), that operates on an entity and returns
> > > a remote pad, with a guarantee that only one link is enabled. To ease
> > > its use in drivers, also add an inline wrapper that locates source pads
> > > specifically. A wrapper that locates sink pads can easily be added when
> > > needed.
> > > 
> > > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > ---
> > >  Documentation/driver-api/media/mc-core.rst |  4 +-
> > >  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> > >  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> > >  3 files changed, 85 insertions(+), 2 deletions(-)
> > > 
> > > diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> > > index 02481a2513b9..a2d1e32e3abb 100644
> > > --- a/Documentation/driver-api/media/mc-core.rst
> > > +++ b/Documentation/driver-api/media/mc-core.rst
> > > @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> > >  
> > >  Helper functions can be used to find a link between two given pads, or a pad
> > >  connected to another pad through an enabled link
> > > -:c:func:`media_entity_find_link()` and
> > > -:c:func:`media_entity_remote_pad()`.
> > > +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> > > +:c:func:`media_entity_remote_source_pad()`).
> > >  
> > >  Use count and power handling
> > >  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> > > diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> > > index 11f5207f73aa..1febf5a86be6 100644
> > > --- a/drivers/media/mc/mc-entity.c
> > > +++ b/drivers/media/mc/mc-entity.c
> > > @@ -9,6 +9,7 @@
> > >   */
> > >  
> > >  #include <linux/bitmap.h>
> > > +#include <linux/list.h>
> > >  #include <linux/property.h>
> > >  #include <linux/slab.h>
> > >  #include <media/media-entity.h>
> > > @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> > >  }
> > >  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> > >  
> > > +struct media_pad *
> > > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > > +			       unsigned int type)
> > > +{
> > > +	struct media_pad *pad = NULL;
> > > +	struct media_link *link;
> > > +
> > > +	list_for_each_entry(link, &entity->links, list) {
> > > +		struct media_pad *local_pad;
> > > +		struct media_pad *remote_pad;
> > > +
> > > +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> > > +			continue;
> > > +
> > > +		if (type == MEDIA_PAD_FL_SOURCE) {
> > > +			local_pad = link->sink;
> > > +			remote_pad = link->source;
> > > +		} else {
> > > +			local_pad = link->source;
> > > +			remote_pad = link->sink;
> > > +		}
> > > +
> > > +		if (local_pad->entity == entity) {
> > > +			if (pad)
> > > +				return ERR_PTR(-ENOTUNIQ);
> > > +
> > > +			pad = remote_pad;
> > > +		}
> > > +	}
> > > +
> > > +	if (!pad)
> > > +		return ERR_PTR(-ENOLINK);
> > > +
> > > +	return pad;
> > > +}
> > > +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> > > +
> > >  static void media_interface_init(struct media_device *mdev,
> > >  				 struct media_interface *intf,
> > >  				 u32 gobj_type,
> > > diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> > > index a9a1c0ec5d1c..33d5f52719a0 100644
> > > --- a/include/media/media-entity.h
> > > +++ b/include/media/media-entity.h
> > > @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> > >   */
> > >  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> > >  
> > > +/**
> > > + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> > > + * @entity: The entity
> > > + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> > > + *
> > > + * Search for and return a remote pad of @type connected to @entity through an
> > > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > > + * is returned.
> > > + *
> > > + * The uniqueness constraint makes this helper function suitable for entities
> > > + * that support a single active source or sink at a time.
> > > + *
> > > + * Return: A pointer to the remote pad, or one of the following error pointers
> > > + * if an error occurs:
> > > + *
> > > + * * -ENOTUNIQ - Multiple links are enabled
> > > + * * -ENOLINK - No connected pad found
> > > + */
> > > +struct media_pad *
> > > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > > +			       unsigned int type);
> > > +
> > > +/**
> > > + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> > > + * @entity: The entity
> > > + *
> > > + * Search for and return a remote source pad connected to @entity through an
> > > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > > + * is returned.
> > > + *
> > > + * The uniqueness constraint makes this helper function suitable for entities
> > > + * that support a single active source at a time.
> > > + *
> > > + * Return: A pointer to the remote pad, or one of the following error pointers
> > > + * if an error occurs:
> > > + *
> > > + * * -ENOTUNIQ - Multiple links are enabled
> > > + * * -ENOLINK - No connected pad found
> > > + */
> > > +static inline struct media_pad *
> > > +media_entity_remote_source_pad(const struct media_entity *entity)
> > > +{
> > > +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> > > +}
> > > +
> > >  /**
> > >   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> > >   * @entity: The entity

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-25 17:28         ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:28 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Sat, Jun 25, 2022 at 08:00:51PM +0300, Laurent Pinchart wrote:
> On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
> > On 6/14/22 21:11, Paul Elder wrote:
> > > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > 
> > > The media_entity_remote_pad() helper function returns the first remote
> > > pad it find connected to a given pad. Beside being possibly ill-named
> > > (as it operates on a pad, not an entity) and non-deterministic (as it
> > > stops at the first enabled link), the fact that it returns the first
> > > match makes it unsuitable for drivers that need to guarantee that a
> > > single link is enabled, for instance when an entity can process data
> > > from one of multiple sources at a time.
> > 
> > Question: of all the callers of this function, are there any that really
> > need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
> > 
> > Would it be possible to replace all callers of the old function with the
> > new function? If that's the case, then the _unique suffix can be dropped,
> > since that would effectively be the default. And if a function is needed
> > to handle the case where there are multiple enabled links, then a new
> > function should be created.
> 
> I don't think so. media_entity_remote_pad() operates on a pad, switching
> to media_pad_remote_pad_unique() wouldn't work on subdevs that have
> multiple sink or source pads with one active link each.
> 
> > Also, media_entity_remote_pad() should really be renamed to
> > media_pad_remote_pad_first() or something like that, right? I'm not saying
> > you should, but that's really what it does, as I understand it.
> 
> Yes, I think that would make sense, and it would freethe
> media_entity_remote_pad() name, so the new function wouldn't need the
> _unique suffix. I'll give it a try.

The rename was easy enough, but I've decided to keep the
media_entity_remote_pad_unique() name and renamed
media_entity_remote_source_pad() to
media_entity_remote_source_pad_unique() to make the API clearer. If
those names end up being too long, we can rename them later.

> > > For those use cases, add a new helper function,
> > > media_entity_remote_pad_unique(), that operates on an entity and returns
> > > a remote pad, with a guarantee that only one link is enabled. To ease
> > > its use in drivers, also add an inline wrapper that locates source pads
> > > specifically. A wrapper that locates sink pads can easily be added when
> > > needed.
> > > 
> > > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > > ---
> > >  Documentation/driver-api/media/mc-core.rst |  4 +-
> > >  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> > >  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> > >  3 files changed, 85 insertions(+), 2 deletions(-)
> > > 
> > > diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> > > index 02481a2513b9..a2d1e32e3abb 100644
> > > --- a/Documentation/driver-api/media/mc-core.rst
> > > +++ b/Documentation/driver-api/media/mc-core.rst
> > > @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> > >  
> > >  Helper functions can be used to find a link between two given pads, or a pad
> > >  connected to another pad through an enabled link
> > > -:c:func:`media_entity_find_link()` and
> > > -:c:func:`media_entity_remote_pad()`.
> > > +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> > > +:c:func:`media_entity_remote_source_pad()`).
> > >  
> > >  Use count and power handling
> > >  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> > > diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> > > index 11f5207f73aa..1febf5a86be6 100644
> > > --- a/drivers/media/mc/mc-entity.c
> > > +++ b/drivers/media/mc/mc-entity.c
> > > @@ -9,6 +9,7 @@
> > >   */
> > >  
> > >  #include <linux/bitmap.h>
> > > +#include <linux/list.h>
> > >  #include <linux/property.h>
> > >  #include <linux/slab.h>
> > >  #include <media/media-entity.h>
> > > @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> > >  }
> > >  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> > >  
> > > +struct media_pad *
> > > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > > +			       unsigned int type)
> > > +{
> > > +	struct media_pad *pad = NULL;
> > > +	struct media_link *link;
> > > +
> > > +	list_for_each_entry(link, &entity->links, list) {
> > > +		struct media_pad *local_pad;
> > > +		struct media_pad *remote_pad;
> > > +
> > > +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> > > +			continue;
> > > +
> > > +		if (type == MEDIA_PAD_FL_SOURCE) {
> > > +			local_pad = link->sink;
> > > +			remote_pad = link->source;
> > > +		} else {
> > > +			local_pad = link->source;
> > > +			remote_pad = link->sink;
> > > +		}
> > > +
> > > +		if (local_pad->entity == entity) {
> > > +			if (pad)
> > > +				return ERR_PTR(-ENOTUNIQ);
> > > +
> > > +			pad = remote_pad;
> > > +		}
> > > +	}
> > > +
> > > +	if (!pad)
> > > +		return ERR_PTR(-ENOLINK);
> > > +
> > > +	return pad;
> > > +}
> > > +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> > > +
> > >  static void media_interface_init(struct media_device *mdev,
> > >  				 struct media_interface *intf,
> > >  				 u32 gobj_type,
> > > diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> > > index a9a1c0ec5d1c..33d5f52719a0 100644
> > > --- a/include/media/media-entity.h
> > > +++ b/include/media/media-entity.h
> > > @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> > >   */
> > >  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> > >  
> > > +/**
> > > + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> > > + * @entity: The entity
> > > + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> > > + *
> > > + * Search for and return a remote pad of @type connected to @entity through an
> > > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > > + * is returned.
> > > + *
> > > + * The uniqueness constraint makes this helper function suitable for entities
> > > + * that support a single active source or sink at a time.
> > > + *
> > > + * Return: A pointer to the remote pad, or one of the following error pointers
> > > + * if an error occurs:
> > > + *
> > > + * * -ENOTUNIQ - Multiple links are enabled
> > > + * * -ENOLINK - No connected pad found
> > > + */
> > > +struct media_pad *
> > > +media_entity_remote_pad_unique(const struct media_entity *entity,
> > > +			       unsigned int type);
> > > +
> > > +/**
> > > + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> > > + * @entity: The entity
> > > + *
> > > + * Search for and return a remote source pad connected to @entity through an
> > > + * enabled link. If multiple (or no) remote pads match these criteria, an error
> > > + * is returned.
> > > + *
> > > + * The uniqueness constraint makes this helper function suitable for entities
> > > + * that support a single active source at a time.
> > > + *
> > > + * Return: A pointer to the remote pad, or one of the following error pointers
> > > + * if an error occurs:
> > > + *
> > > + * * -ENOTUNIQ - Multiple links are enabled
> > > + * * -ENOLINK - No connected pad found
> > > + */
> > > +static inline struct media_pad *
> > > +media_entity_remote_source_pad(const struct media_entity *entity)
> > > +{
> > > +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> > > +}
> > > +
> > >  /**
> > >   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> > >   * @entity: The entity

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-18  9:35           ` Daniel Scally
@ 2022-06-25 17:34             ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:34 UTC (permalink / raw)
  To: Daniel Scally
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, helen.koike, linux-rockchip

Hi Dan,

On Sat, Jun 18, 2022 at 10:35:12AM +0100, Daniel Scally wrote:
> On 17/06/2022 23:40, Laurent Pinchart wrote:
> > On Fri, Jun 17, 2022 at 11:33:03PM +0100, Daniel Scally wrote:
> >> On 17/06/2022 22:34, Daniel Scally wrote:
> >>> On 14/06/2022 20:11, Paul Elder wrote:
> >>>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>>>
> >>>> The media_entity_remote_pad() helper function returns the first remote
> >>>> pad it find connected to a given pad. Beside being possibly ill-named
> >>>> (as it operates on a pad, not an entity) and non-deterministic (as it
> >>>> stops at the first enabled link), the fact that it returns the first
> >>>> match makes it unsuitable for drivers that need to guarantee that a
> >>>> single link is enabled, for instance when an entity can process data
> >>>> from one of multiple sources at a time.
> >>>>
> >>>> For those use cases, add a new helper function,
> >>>> media_entity_remote_pad_unique(), that operates on an entity and returns
> >>>> a remote pad, with a guarantee that only one link is enabled. To ease
> >>>> its use in drivers, also add an inline wrapper that locates source pads
> >>>> specifically. A wrapper that locates sink pads can easily be added when
> >>>> needed.
> >>>>
> >>>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>>> ---
> >>>>  Documentation/driver-api/media/mc-core.rst |  4 +-
> >>>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >>>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >>>>  3 files changed, 85 insertions(+), 2 deletions(-)
> >>>>
> >>>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> >>>> index 02481a2513b9..a2d1e32e3abb 100644
> >>>> --- a/Documentation/driver-api/media/mc-core.rst
> >>>> +++ b/Documentation/driver-api/media/mc-core.rst
> >>>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >>>>  
> >>>>  Helper functions can be used to find a link between two given pads, or a pad
> >>>>  connected to another pad through an enabled link
> >>>> -:c:func:`media_entity_find_link()` and
> >>>> -:c:func:`media_entity_remote_pad()`.
> >>>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> >>>> +:c:func:`media_entity_remote_source_pad()`).
> >>>>  
> >>>>  Use count and power handling
> >>>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> >>>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> >>>> index 11f5207f73aa..1febf5a86be6 100644
> >>>> --- a/drivers/media/mc/mc-entity.c
> >>>> +++ b/drivers/media/mc/mc-entity.c
> >>>> @@ -9,6 +9,7 @@
> >>>>   */
> >>>>  
> >>>>  #include <linux/bitmap.h>
> >>>> +#include <linux/list.h>
> >>>>  #include <linux/property.h>
> >>>>  #include <linux/slab.h>
> >>>>  #include <media/media-entity.h>
> >>>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >>>>  }
> >>>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >>>>  
> >>>> +struct media_pad *
> >>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>>> +			       unsigned int type)
> >>>> +{
> >>>> +	struct media_pad *pad = NULL;
> >>>> +	struct media_link *link;
> >>>> +
> >>>> +	list_for_each_entry(link, &entity->links, list) {
> >>>> +		struct media_pad *local_pad;
> >>>> +		struct media_pad *remote_pad;
> >>>> +
> >>>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> >>>> +			continue;
> >>> 
> >>> Does this need another guard here to make sure the link isn't an
> >>> ancillary link? Only likely to happen at least in the immediate future
> >>> where the entity represents a camera sensor, so possibly not applicable
> >>> here - I couldn't find where the new function is used in the series to
> >>> check. I _think_ it would actually work ok regardless...media_gobj
> >>> type-punning makes my brain ache, but I think the local_pad->entity ==
> >>> entity comparison would actually compare the entity->name member of the
> >>> entity at the end of an ancillary link to the entity parameter, not find
> >>> a match and so continue the loop without failing, but that feels a bit
> >>> sub-optimal.
> >> 
> >> Or perhaps a better approach would be to provide something like a
> >> "list_for_each_data_link()" iterator - the potential problem here (as
> >> with Quentin's recent issue with the rkisp1 driver) is the assumption
> >> that all links are data links, so maybe it's best to just guarantee that
> >> if we can.
> >> 
> > I agree with you, without a dedicated iterator, we're bound to repeat
> > the mistake over and over.
> >
> > Would you like to submit a patch to add that iterator, or should I ? I'd
> > name it for_each_media_entity_data_link() or something similar.
> 
> I've started one - I'll send it later (using your function name though,
> naming things was never my strong suit!)

I've modified this patch to skip non-data links manually, to avoid
depending on your series. If the iterator gets merged first, I'll update
the media_entity_remote_pad_unique() helper to use it.

> >>>> +
> >>>> +		if (type == MEDIA_PAD_FL_SOURCE) {
> >>>> +			local_pad = link->sink;
> >>>> +			remote_pad = link->source;
> >>>> +		} else {
> >>>> +			local_pad = link->source;
> >>>> +			remote_pad = link->sink;
> >>>> +		}
> >>>> +
> >>>> +		if (local_pad->entity == entity) {
> >>>> +			if (pad)
> >>>> +				return ERR_PTR(-ENOTUNIQ);
> >>>> +
> >>>> +			pad = remote_pad;
> >>>> +		}
> >>>> +	}
> >>>> +
> >>>> +	if (!pad)
> >>>> +		return ERR_PTR(-ENOLINK);
> >>>> +
> >>>> +	return pad;
> >>>> +}
> >>>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >>>> +
> >>>>  static void media_interface_init(struct media_device *mdev,
> >>>>  				 struct media_interface *intf,
> >>>>  				 u32 gobj_type,
> >>>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> >>>> index a9a1c0ec5d1c..33d5f52719a0 100644
> >>>> --- a/include/media/media-entity.h
> >>>> +++ b/include/media/media-entity.h
> >>>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >>>>   */
> >>>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >>>>  
> >>>> +/**
> >>>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> >>>> + * @entity: The entity
> >>>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> >>>> + *
> >>>> + * Search for and return a remote pad of @type connected to @entity through an
> >>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>>> + * is returned.
> >>>> + *
> >>>> + * The uniqueness constraint makes this helper function suitable for entities
> >>>> + * that support a single active source or sink at a time.
> >>>> + *
> >>>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>>> + * if an error occurs:
> >>>> + *
> >>>> + * * -ENOTUNIQ - Multiple links are enabled
> >>>> + * * -ENOLINK - No connected pad found
> >>>> + */
> >>>> +struct media_pad *
> >>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>>> +			       unsigned int type);
> >>>> +
> >>>> +/**
> >>>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> >>>> + * @entity: The entity
> >>>> + *
> >>>> + * Search for and return a remote source pad connected to @entity through an
> >>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>>> + * is returned.
> >>>> + *
> >>>> + * The uniqueness constraint makes this helper function suitable for entities
> >>>> + * that support a single active source at a time.
> >>>> + *
> >>>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>>> + * if an error occurs:
> >>>> + *
> >>>> + * * -ENOTUNIQ - Multiple links are enabled
> >>>> + * * -ENOLINK - No connected pad found
> >>>> + */
> >>>> +static inline struct media_pad *
> >>>> +media_entity_remote_source_pad(const struct media_entity *entity)
> >>>> +{
> >>>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >>>> +}
> >>>> +
> >>>>  /**
> >>>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >>>>   * @entity: The entity

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-06-25 17:34             ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:34 UTC (permalink / raw)
  To: Daniel Scally
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, helen.koike, linux-rockchip

Hi Dan,

On Sat, Jun 18, 2022 at 10:35:12AM +0100, Daniel Scally wrote:
> On 17/06/2022 23:40, Laurent Pinchart wrote:
> > On Fri, Jun 17, 2022 at 11:33:03PM +0100, Daniel Scally wrote:
> >> On 17/06/2022 22:34, Daniel Scally wrote:
> >>> On 14/06/2022 20:11, Paul Elder wrote:
> >>>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>>>
> >>>> The media_entity_remote_pad() helper function returns the first remote
> >>>> pad it find connected to a given pad. Beside being possibly ill-named
> >>>> (as it operates on a pad, not an entity) and non-deterministic (as it
> >>>> stops at the first enabled link), the fact that it returns the first
> >>>> match makes it unsuitable for drivers that need to guarantee that a
> >>>> single link is enabled, for instance when an entity can process data
> >>>> from one of multiple sources at a time.
> >>>>
> >>>> For those use cases, add a new helper function,
> >>>> media_entity_remote_pad_unique(), that operates on an entity and returns
> >>>> a remote pad, with a guarantee that only one link is enabled. To ease
> >>>> its use in drivers, also add an inline wrapper that locates source pads
> >>>> specifically. A wrapper that locates sink pads can easily be added when
> >>>> needed.
> >>>>
> >>>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>>> ---
> >>>>  Documentation/driver-api/media/mc-core.rst |  4 +-
> >>>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >>>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >>>>  3 files changed, 85 insertions(+), 2 deletions(-)
> >>>>
> >>>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> >>>> index 02481a2513b9..a2d1e32e3abb 100644
> >>>> --- a/Documentation/driver-api/media/mc-core.rst
> >>>> +++ b/Documentation/driver-api/media/mc-core.rst
> >>>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >>>>  
> >>>>  Helper functions can be used to find a link between two given pads, or a pad
> >>>>  connected to another pad through an enabled link
> >>>> -:c:func:`media_entity_find_link()` and
> >>>> -:c:func:`media_entity_remote_pad()`.
> >>>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> >>>> +:c:func:`media_entity_remote_source_pad()`).
> >>>>  
> >>>>  Use count and power handling
> >>>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> >>>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> >>>> index 11f5207f73aa..1febf5a86be6 100644
> >>>> --- a/drivers/media/mc/mc-entity.c
> >>>> +++ b/drivers/media/mc/mc-entity.c
> >>>> @@ -9,6 +9,7 @@
> >>>>   */
> >>>>  
> >>>>  #include <linux/bitmap.h>
> >>>> +#include <linux/list.h>
> >>>>  #include <linux/property.h>
> >>>>  #include <linux/slab.h>
> >>>>  #include <media/media-entity.h>
> >>>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >>>>  }
> >>>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >>>>  
> >>>> +struct media_pad *
> >>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>>> +			       unsigned int type)
> >>>> +{
> >>>> +	struct media_pad *pad = NULL;
> >>>> +	struct media_link *link;
> >>>> +
> >>>> +	list_for_each_entry(link, &entity->links, list) {
> >>>> +		struct media_pad *local_pad;
> >>>> +		struct media_pad *remote_pad;
> >>>> +
> >>>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> >>>> +			continue;
> >>> 
> >>> Does this need another guard here to make sure the link isn't an
> >>> ancillary link? Only likely to happen at least in the immediate future
> >>> where the entity represents a camera sensor, so possibly not applicable
> >>> here - I couldn't find where the new function is used in the series to
> >>> check. I _think_ it would actually work ok regardless...media_gobj
> >>> type-punning makes my brain ache, but I think the local_pad->entity ==
> >>> entity comparison would actually compare the entity->name member of the
> >>> entity at the end of an ancillary link to the entity parameter, not find
> >>> a match and so continue the loop without failing, but that feels a bit
> >>> sub-optimal.
> >> 
> >> Or perhaps a better approach would be to provide something like a
> >> "list_for_each_data_link()" iterator - the potential problem here (as
> >> with Quentin's recent issue with the rkisp1 driver) is the assumption
> >> that all links are data links, so maybe it's best to just guarantee that
> >> if we can.
> >> 
> > I agree with you, without a dedicated iterator, we're bound to repeat
> > the mistake over and over.
> >
> > Would you like to submit a patch to add that iterator, or should I ? I'd
> > name it for_each_media_entity_data_link() or something similar.
> 
> I've started one - I'll send it later (using your function name though,
> naming things was never my strong suit!)

I've modified this patch to skip non-data links manually, to avoid
depending on your series. If the iterator gets merged first, I'll update
the media_entity_remote_pad_unique() helper to use it.

> >>>> +
> >>>> +		if (type == MEDIA_PAD_FL_SOURCE) {
> >>>> +			local_pad = link->sink;
> >>>> +			remote_pad = link->source;
> >>>> +		} else {
> >>>> +			local_pad = link->source;
> >>>> +			remote_pad = link->sink;
> >>>> +		}
> >>>> +
> >>>> +		if (local_pad->entity == entity) {
> >>>> +			if (pad)
> >>>> +				return ERR_PTR(-ENOTUNIQ);
> >>>> +
> >>>> +			pad = remote_pad;
> >>>> +		}
> >>>> +	}
> >>>> +
> >>>> +	if (!pad)
> >>>> +		return ERR_PTR(-ENOLINK);
> >>>> +
> >>>> +	return pad;
> >>>> +}
> >>>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >>>> +
> >>>>  static void media_interface_init(struct media_device *mdev,
> >>>>  				 struct media_interface *intf,
> >>>>  				 u32 gobj_type,
> >>>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> >>>> index a9a1c0ec5d1c..33d5f52719a0 100644
> >>>> --- a/include/media/media-entity.h
> >>>> +++ b/include/media/media-entity.h
> >>>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >>>>   */
> >>>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >>>>  
> >>>> +/**
> >>>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> >>>> + * @entity: The entity
> >>>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> >>>> + *
> >>>> + * Search for and return a remote pad of @type connected to @entity through an
> >>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>>> + * is returned.
> >>>> + *
> >>>> + * The uniqueness constraint makes this helper function suitable for entities
> >>>> + * that support a single active source or sink at a time.
> >>>> + *
> >>>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>>> + * if an error occurs:
> >>>> + *
> >>>> + * * -ENOTUNIQ - Multiple links are enabled
> >>>> + * * -ENOLINK - No connected pad found
> >>>> + */
> >>>> +struct media_pad *
> >>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>>> +			       unsigned int type);
> >>>> +
> >>>> +/**
> >>>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> >>>> + * @entity: The entity
> >>>> + *
> >>>> + * Search for and return a remote source pad connected to @entity through an
> >>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>>> + * is returned.
> >>>> + *
> >>>> + * The uniqueness constraint makes this helper function suitable for entities
> >>>> + * that support a single active source at a time.
> >>>> + *
> >>>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>>> + * if an error occurs:
> >>>> + *
> >>>> + * * -ENOTUNIQ - Multiple links are enabled
> >>>> + * * -ENOLINK - No connected pad found
> >>>> + */
> >>>> +static inline struct media_pad *
> >>>> +media_entity_remote_source_pad(const struct media_entity *entity)
> >>>> +{
> >>>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >>>> +}
> >>>> +
> >>>>  /**
> >>>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >>>>   * @entity: The entity

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
  2022-06-15 22:41     ` Laurent Pinchart
@ 2022-06-25 17:59       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:59 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

On Thu, Jun 16, 2022 at 01:41:56AM +0300, Laurent Pinchart wrote:
> On Wed, Jun 15, 2022 at 04:10:33AM +0900, Paul Elder wrote:
> > Add a register dump file in debugfs for some of the buffer-related
> > registers in MI, for the base address, the size, and the offset. Also
> > dump the appropriate shadow registers.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
> >  1 file changed, 21 insertions(+)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > index e76dc2b164b6..1a59c00fabdd 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > @@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> >  }
> >  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
> >  
> > +static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
> > +{
> > +	static const struct rkisp1_debug_register registers[] = {
> > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
> > +		{ /* Sentinel */ },
> > +	};
> > +	struct rkisp1_device *rkisp1 = m->private;
> > +
> > +	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
> > +}
> > +DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
> > +
> >  #define RKISP1_DEBUG_DATA_COUNT_BINS	32
> >  #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
> >  
> > @@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
> >  	debugfs_create_file("srsz", 0444, regs_dir,
> >  			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
> >  			    &rkisp1_debug_dump_rsz_regs_fops);
> > +
> > +	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
> > +			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);
> 
> That's a very specialized file. I wonder if we should call it just
> "mi_mp" if it needs to be extended later with other memory interface
> registers for the main path. Or maybe even just "mi", to cover the self
> path too ? The latter may be a tad too generic. What do you think ?

Ping

> >  }
> >  
> >  void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
@ 2022-06-25 17:59       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-25 17:59 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

On Thu, Jun 16, 2022 at 01:41:56AM +0300, Laurent Pinchart wrote:
> On Wed, Jun 15, 2022 at 04:10:33AM +0900, Paul Elder wrote:
> > Add a register dump file in debugfs for some of the buffer-related
> > registers in MI, for the base address, the size, and the offset. Also
> > dump the appropriate shadow registers.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
> >  1 file changed, 21 insertions(+)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > index e76dc2b164b6..1a59c00fabdd 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > @@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> >  }
> >  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
> >  
> > +static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
> > +{
> > +	static const struct rkisp1_debug_register registers[] = {
> > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
> > +		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
> > +		{ /* Sentinel */ },
> > +	};
> > +	struct rkisp1_device *rkisp1 = m->private;
> > +
> > +	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
> > +}
> > +DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
> > +
> >  #define RKISP1_DEBUG_DATA_COUNT_BINS	32
> >  #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
> >  
> > @@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
> >  	debugfs_create_file("srsz", 0444, regs_dir,
> >  			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
> >  			    &rkisp1_debug_dump_rsz_regs_fops);
> > +
> > +	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
> > +			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);
> 
> That's a very specialized file. I wonder if we should call it just
> "mi_mp" if it needs to be extended later with other memory interface
> registers for the main path. Or maybe even just "mi", to cover the self
> path too ? The latter may be a tad too generic. What do you think ?

Ping

> >  }
> >  
> >  void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
  2022-06-17 23:26     ` Laurent Pinchart
@ 2022-06-26  4:05       ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-26  4:05 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 18.06.2022 02:26, Laurent Pinchart wrote:
>Hi Paul,
>
>Thank you for the patch.
>
>On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
>> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
>>
>> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>> ---
>>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
>>  include/uapi/linux/rkisp1-config.h            |  3 +++
>>  2 files changed, 25 insertions(+)
>>
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> index 62fa2bd275fe..3a0115bdcee5 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
>>  	.features = RKISP1_FEATURE_MIPI_CSI2,
>>  };
>>
>> +static const char * const imx8mp_isp_clks[] = {
>> +	"isp",
>> +	"hclk",
>> +	"aclk",
>> +};
>> +
>> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
>> +	{ NULL, rkisp1_isr },
>> +};
>> +
>> +static const struct rkisp1_info imx8mp_isp_info = {
>> +	.clks = imx8mp_isp_clks,
>> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
>> +	.isrs = imx8mp_isp_isrs,
>> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>> +	.isp_ver = IMX8MP_V10,
>> +};
>> +
>>  static const struct of_device_id rkisp1_of_match[] = {
>>  	{
>>  		.compatible = "rockchip,px30-cif-isp",
>> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
>>  		.compatible = "rockchip,rk3399-cif-isp",
>>  		.data = &rk3399_isp_info,
>>  	},
>> +	{
>> +		.compatible = "fsl,imx8mp-isp",
>> +		.data = &imx8mp_isp_info,
>> +	},
>>  	{},
>>  };
>>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
>> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
>> index 583ca0d9a79d..40677d47825c 100644
>> --- a/include/uapi/linux/rkisp1-config.h
>> +++ b/include/uapi/linux/rkisp1-config.h
>> @@ -140,12 +140,15 @@
>>   * @RKISP1_V11: declared in the original vendor code, but not used
>>   * @RKISP1_V12: used at least in rk3326 and px30
>>   * @RKISP1_V13: used at least in rk1808
>> + * @IMX8MP_V10: used in at least imx8mp
>>   */
>>  enum rkisp1_cif_isp_version {
>>  	RKISP1_V10 = 10,
>>  	RKISP1_V11,
>>  	RKISP1_V12,
>>  	RKISP1_V13,
>> +	/* TODO Choose a better version for this */
>> +	IMX8MP_V10,
>
>Time to address this ? :-)
>
>Does anyone know where the current versioning scheme come from ?

It was added by Heiko Stübner, basically trying to figure out the
versions from the vedor code,
see https://lore.kernel.org/all/20210121144407.9045-6-dafna.hirschfeld@collabora.com/

thanks,
Dafna

>
>>  };
>>
>>  enum rkisp1_cif_isp_histogram_mode {
>
>-- 
>Regards,
>
>Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
@ 2022-06-26  4:05       ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-26  4:05 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 18.06.2022 02:26, Laurent Pinchart wrote:
>Hi Paul,
>
>Thank you for the patch.
>
>On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
>> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
>>
>> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>> ---
>>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
>>  include/uapi/linux/rkisp1-config.h            |  3 +++
>>  2 files changed, 25 insertions(+)
>>
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> index 62fa2bd275fe..3a0115bdcee5 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
>>  	.features = RKISP1_FEATURE_MIPI_CSI2,
>>  };
>>
>> +static const char * const imx8mp_isp_clks[] = {
>> +	"isp",
>> +	"hclk",
>> +	"aclk",
>> +};
>> +
>> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
>> +	{ NULL, rkisp1_isr },
>> +};
>> +
>> +static const struct rkisp1_info imx8mp_isp_info = {
>> +	.clks = imx8mp_isp_clks,
>> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
>> +	.isrs = imx8mp_isp_isrs,
>> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>> +	.isp_ver = IMX8MP_V10,
>> +};
>> +
>>  static const struct of_device_id rkisp1_of_match[] = {
>>  	{
>>  		.compatible = "rockchip,px30-cif-isp",
>> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
>>  		.compatible = "rockchip,rk3399-cif-isp",
>>  		.data = &rk3399_isp_info,
>>  	},
>> +	{
>> +		.compatible = "fsl,imx8mp-isp",
>> +		.data = &imx8mp_isp_info,
>> +	},
>>  	{},
>>  };
>>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
>> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
>> index 583ca0d9a79d..40677d47825c 100644
>> --- a/include/uapi/linux/rkisp1-config.h
>> +++ b/include/uapi/linux/rkisp1-config.h
>> @@ -140,12 +140,15 @@
>>   * @RKISP1_V11: declared in the original vendor code, but not used
>>   * @RKISP1_V12: used at least in rk3326 and px30
>>   * @RKISP1_V13: used at least in rk1808
>> + * @IMX8MP_V10: used in at least imx8mp
>>   */
>>  enum rkisp1_cif_isp_version {
>>  	RKISP1_V10 = 10,
>>  	RKISP1_V11,
>>  	RKISP1_V12,
>>  	RKISP1_V13,
>> +	/* TODO Choose a better version for this */
>> +	IMX8MP_V10,
>
>Time to address this ? :-)
>
>Does anyone know where the current versioning scheme come from ?

It was added by Heiko Stübner, basically trying to figure out the
versions from the vedor code,
see https://lore.kernel.org/all/20210121144407.9045-6-dafna.hirschfeld@collabora.com/

thanks,
Dafna

>
>>  };
>>
>>  enum rkisp1_cif_isp_histogram_mode {
>
>-- 
>Regards,
>
>Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
  2022-06-26  4:05       ` Dafna Hirschfeld
@ 2022-06-26 11:07         ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:07 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On Sun, Jun 26, 2022 at 07:05:43AM +0300, Dafna Hirschfeld wrote:
> On 18.06.2022 02:26, Laurent Pinchart wrote:
> > On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
> >> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
> >>
> >> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> >> ---
> >>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
> >>  include/uapi/linux/rkisp1-config.h            |  3 +++
> >>  2 files changed, 25 insertions(+)
> >>
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> index 62fa2bd275fe..3a0115bdcee5 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
> >>  	.features = RKISP1_FEATURE_MIPI_CSI2,
> >>  };
> >>
> >> +static const char * const imx8mp_isp_clks[] = {
> >> +	"isp",
> >> +	"hclk",
> >> +	"aclk",
> >> +};
> >> +
> >> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
> >> +	{ NULL, rkisp1_isr },
> >> +};
> >> +
> >> +static const struct rkisp1_info imx8mp_isp_info = {
> >> +	.clks = imx8mp_isp_clks,
> >> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
> >> +	.isrs = imx8mp_isp_isrs,
> >> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> >> +	.isp_ver = IMX8MP_V10,
> >> +};
> >> +
> >>  static const struct of_device_id rkisp1_of_match[] = {
> >>  	{
> >>  		.compatible = "rockchip,px30-cif-isp",
> >> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
> >>  		.compatible = "rockchip,rk3399-cif-isp",
> >>  		.data = &rk3399_isp_info,
> >>  	},
> >> +	{
> >> +		.compatible = "fsl,imx8mp-isp",
> >> +		.data = &imx8mp_isp_info,
> >> +	},
> >>  	{},
> >>  };
> >>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
> >> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
> >> index 583ca0d9a79d..40677d47825c 100644
> >> --- a/include/uapi/linux/rkisp1-config.h
> >> +++ b/include/uapi/linux/rkisp1-config.h
> >> @@ -140,12 +140,15 @@
> >>   * @RKISP1_V11: declared in the original vendor code, but not used
> >>   * @RKISP1_V12: used at least in rk3326 and px30
> >>   * @RKISP1_V13: used at least in rk1808
> >> + * @IMX8MP_V10: used in at least imx8mp
> >>   */
> >>  enum rkisp1_cif_isp_version {
> >>  	RKISP1_V10 = 10,
> >>  	RKISP1_V11,
> >>  	RKISP1_V12,
> >>  	RKISP1_V13,
> >> +	/* TODO Choose a better version for this */
> >> +	IMX8MP_V10,
> >
> > Time to address this ? :-)
> >
> > Does anyone know where the current versioning scheme come from ?
> 
> It was added by Heiko Stübner, basically trying to figure out the
> versions from the vedor code,
> see https://lore.kernel.org/all/20210121144407.9045-6-dafna.hirschfeld@collabora.com/

Is that public code ? Heiko, do you have any pointer to it ?

As far as I understand, this ISP IP has been forked, and is now
developed in parallel by Rockchip (for their own SoCs) and by
VeriSilicon (under the name of ISP8000Nano). The versioning schemes on
the two sides are different, and may have common roots. The fact that
the ISP8000Nano can be customized at synthesis time also complicates
this.

The question at hand is how to expose a single coherent versioning
scheme to userspace in this driver. The hardware has a version
identification register that we could use, but I don't know if it gives
us enough information (as in guaranteeing that the same version value
won't be used for different IP versions that would need to be
distinguished from each other in userspace). The fact that Rockchip and
VeriSilicon probably develop their own new versions without cooperating
increases the risk of collision.

We will also have to tackle the question of UABI. Newer ISP versions
will require extensions to the ISP parameters structure. The i.MX8MP has
extra processing blocks that are not supported by the driver today. One
option would be to duplicate the top-level rkisp1_params_cfg structure
per ISP version, as well as a set of lower-level structure where
appropriate (how to handle that easily and efficiently on the driver
side will be interesting to figure out). Another option is to only add
parameters to the end of the rkisp1_params_cfg structure, but I fear
that won't scale. We'll end up with a large structure where lots of data
will be irrelevant for any particular ISP version, and that will be
error-prone.

Comments and idea will be appreciated.

> >>  };
> >>
> >>  enum rkisp1_cif_isp_histogram_mode {

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
@ 2022-06-26 11:07         ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:07 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On Sun, Jun 26, 2022 at 07:05:43AM +0300, Dafna Hirschfeld wrote:
> On 18.06.2022 02:26, Laurent Pinchart wrote:
> > On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
> >> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
> >>
> >> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> >> ---
> >>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
> >>  include/uapi/linux/rkisp1-config.h            |  3 +++
> >>  2 files changed, 25 insertions(+)
> >>
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> index 62fa2bd275fe..3a0115bdcee5 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
> >>  	.features = RKISP1_FEATURE_MIPI_CSI2,
> >>  };
> >>
> >> +static const char * const imx8mp_isp_clks[] = {
> >> +	"isp",
> >> +	"hclk",
> >> +	"aclk",
> >> +};
> >> +
> >> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
> >> +	{ NULL, rkisp1_isr },
> >> +};
> >> +
> >> +static const struct rkisp1_info imx8mp_isp_info = {
> >> +	.clks = imx8mp_isp_clks,
> >> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
> >> +	.isrs = imx8mp_isp_isrs,
> >> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> >> +	.isp_ver = IMX8MP_V10,
> >> +};
> >> +
> >>  static const struct of_device_id rkisp1_of_match[] = {
> >>  	{
> >>  		.compatible = "rockchip,px30-cif-isp",
> >> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
> >>  		.compatible = "rockchip,rk3399-cif-isp",
> >>  		.data = &rk3399_isp_info,
> >>  	},
> >> +	{
> >> +		.compatible = "fsl,imx8mp-isp",
> >> +		.data = &imx8mp_isp_info,
> >> +	},
> >>  	{},
> >>  };
> >>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
> >> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
> >> index 583ca0d9a79d..40677d47825c 100644
> >> --- a/include/uapi/linux/rkisp1-config.h
> >> +++ b/include/uapi/linux/rkisp1-config.h
> >> @@ -140,12 +140,15 @@
> >>   * @RKISP1_V11: declared in the original vendor code, but not used
> >>   * @RKISP1_V12: used at least in rk3326 and px30
> >>   * @RKISP1_V13: used at least in rk1808
> >> + * @IMX8MP_V10: used in at least imx8mp
> >>   */
> >>  enum rkisp1_cif_isp_version {
> >>  	RKISP1_V10 = 10,
> >>  	RKISP1_V11,
> >>  	RKISP1_V12,
> >>  	RKISP1_V13,
> >> +	/* TODO Choose a better version for this */
> >> +	IMX8MP_V10,
> >
> > Time to address this ? :-)
> >
> > Does anyone know where the current versioning scheme come from ?
> 
> It was added by Heiko Stübner, basically trying to figure out the
> versions from the vedor code,
> see https://lore.kernel.org/all/20210121144407.9045-6-dafna.hirschfeld@collabora.com/

Is that public code ? Heiko, do you have any pointer to it ?

As far as I understand, this ISP IP has been forked, and is now
developed in parallel by Rockchip (for their own SoCs) and by
VeriSilicon (under the name of ISP8000Nano). The versioning schemes on
the two sides are different, and may have common roots. The fact that
the ISP8000Nano can be customized at synthesis time also complicates
this.

The question at hand is how to expose a single coherent versioning
scheme to userspace in this driver. The hardware has a version
identification register that we could use, but I don't know if it gives
us enough information (as in guaranteeing that the same version value
won't be used for different IP versions that would need to be
distinguished from each other in userspace). The fact that Rockchip and
VeriSilicon probably develop their own new versions without cooperating
increases the risk of collision.

We will also have to tackle the question of UABI. Newer ISP versions
will require extensions to the ISP parameters structure. The i.MX8MP has
extra processing blocks that are not supported by the driver today. One
option would be to duplicate the top-level rkisp1_params_cfg structure
per ISP version, as well as a set of lower-level structure where
appropriate (how to handle that easily and efficiently on the driver
side will be interesting to figure out). Another option is to only add
parameters to the end of the rkisp1_params_cfg structure, but I fear
that won't scale. We'll end up with a large structure where lots of data
will be irrelevant for any particular ISP version, and that will be
error-prone.

Comments and idea will be appreciated.

> >>  };
> >>
> >>  enum rkisp1_cif_isp_histogram_mode {

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-26 11:38     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:38 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:25AM +0900, Paul Elder wrote:
> On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
> encoded in 34-bit. Shift them to the left by 2 bits so that they can be

I think you meant right, not left.

> contained in 32 bits.

The important part here is that this is how the address is encoded in
the hardware. I suppose it's obvious, otherwise it woudln't work at all,
but maybe it could be explained more explicitly ?

On the ISP that is integrated in the i.MX8MP, DMA addresses have been
extended to 34 bits, with the 32 MSBs stored in the DMA address
registers and the 2 LSBs set to 0. Shift the buffer addresses right by 2
on that platform.

> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
>  3 files changed, 14 insertions(+), 9 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> index 35cec263c563..234b1f8488cb 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> @@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
>  
>  static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  {
> +	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
> +		   2 : 0;
> +
>  	cap->buf.curr = cap->buf.next;
>  	cap->buf.next = NULL;
>  
> @@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  		buff_addr = cap->buf.next->buff_addr;
>  
>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> -			     buff_addr[RKISP1_PLANE_Y]);
> +			     buff_addr[RKISP1_PLANE_Y] >> shift);
>  		/*
>  		 * In order to support grey format we capture
>  		 * YUV422 planar format from the camera and
> @@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cb_base_ad_init,
> -				     cap->buf.dummy.dma_addr);
> +				     cap->buf.dummy.dma_addr >> shift);
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cr_base_ad_init,
> -				     cap->buf.dummy.dma_addr);
> +				     cap->buf.dummy.dma_addr >> shift);
>  		} else {
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cb_base_ad_init,
> -				     buff_addr[RKISP1_PLANE_CB]);
> +				     buff_addr[RKISP1_PLANE_CB] >> shift);
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cr_base_ad_init,
> -				     buff_addr[RKISP1_PLANE_CR]);
> +				     buff_addr[RKISP1_PLANE_CR] >> shift);
>  		}
>  	} else {
>  		/*
> @@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  		 * throw data if there is no available buffer.
>  		 */
>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> -			     cap->buf.dummy.dma_addr);
> +			     cap->buf.dummy.dma_addr >> shift);
>  		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
> -			     cap->buf.dummy.dma_addr);
> +			     cap->buf.dummy.dma_addr >> shift);
>  		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
> -			     cap->buf.dummy.dma_addr);
> +			     cap->buf.dummy.dma_addr >> shift);
>  	}
>  
>  	/* Set plane offsets */
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 96657e55a5b0..0b834579d08c 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -113,6 +113,7 @@ enum rkisp1_feature {
>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>  	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
> +	RKISP1_FEATURE_DMA_34BIT = BIT(4),
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index d68a805e8b6b..4c77aa2bc50a 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>  	.isp_ver = IMX8MP_V10,
>  	.features = RKISP1_FEATURE_RSZ_CROP
> -		  | RKISP1_FEATURE_MAIN_STRIDE,
> +		  | RKISP1_FEATURE_MAIN_STRIDE
> +		  | RKISP1_FEATURE_DMA_34BIT,
>  };
>  
>  static const struct of_device_id rkisp1_of_match[] = {

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
@ 2022-06-26 11:38     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:38 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:25AM +0900, Paul Elder wrote:
> On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
> encoded in 34-bit. Shift them to the left by 2 bits so that they can be

I think you meant right, not left.

> contained in 32 bits.

The important part here is that this is how the address is encoded in
the hardware. I suppose it's obvious, otherwise it woudln't work at all,
but maybe it could be explained more explicitly ?

On the ISP that is integrated in the i.MX8MP, DMA addresses have been
extended to 34 bits, with the 32 MSBs stored in the DMA address
registers and the 2 LSBs set to 0. Shift the buffer addresses right by 2
on that platform.

> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
>  3 files changed, 14 insertions(+), 9 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> index 35cec263c563..234b1f8488cb 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> @@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
>  
>  static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  {
> +	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
> +		   2 : 0;
> +
>  	cap->buf.curr = cap->buf.next;
>  	cap->buf.next = NULL;
>  
> @@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  		buff_addr = cap->buf.next->buff_addr;
>  
>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> -			     buff_addr[RKISP1_PLANE_Y]);
> +			     buff_addr[RKISP1_PLANE_Y] >> shift);
>  		/*
>  		 * In order to support grey format we capture
>  		 * YUV422 planar format from the camera and
> @@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cb_base_ad_init,
> -				     cap->buf.dummy.dma_addr);
> +				     cap->buf.dummy.dma_addr >> shift);
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cr_base_ad_init,
> -				     cap->buf.dummy.dma_addr);
> +				     cap->buf.dummy.dma_addr >> shift);
>  		} else {
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cb_base_ad_init,
> -				     buff_addr[RKISP1_PLANE_CB]);
> +				     buff_addr[RKISP1_PLANE_CB] >> shift);
>  			rkisp1_write(cap->rkisp1,
>  				     cap->config->mi.cr_base_ad_init,
> -				     buff_addr[RKISP1_PLANE_CR]);
> +				     buff_addr[RKISP1_PLANE_CR] >> shift);
>  		}
>  	} else {
>  		/*
> @@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>  		 * throw data if there is no available buffer.
>  		 */
>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> -			     cap->buf.dummy.dma_addr);
> +			     cap->buf.dummy.dma_addr >> shift);
>  		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
> -			     cap->buf.dummy.dma_addr);
> +			     cap->buf.dummy.dma_addr >> shift);
>  		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
> -			     cap->buf.dummy.dma_addr);
> +			     cap->buf.dummy.dma_addr >> shift);
>  	}
>  
>  	/* Set plane offsets */
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 96657e55a5b0..0b834579d08c 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -113,6 +113,7 @@ enum rkisp1_feature {
>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>  	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
> +	RKISP1_FEATURE_DMA_34BIT = BIT(4),
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index d68a805e8b6b..4c77aa2bc50a 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>  	.isp_ver = IMX8MP_V10,
>  	.features = RKISP1_FEATURE_RSZ_CROP
> -		  | RKISP1_FEATURE_MAIN_STRIDE,
> +		  | RKISP1_FEATURE_MAIN_STRIDE
> +		  | RKISP1_FEATURE_DMA_34BIT,
>  };
>  
>  static const struct of_device_id rkisp1_of_match[] = {

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
  2022-06-17 23:03       ` Laurent Pinchart
@ 2022-06-26 11:40         ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:40 UTC (permalink / raw)
  To: Paul Elder
  Cc: Alexander Stein, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Paul,

Ping

On Sat, Jun 18, 2022 at 02:03:19AM +0300, Laurent Pinchart wrote:
> On Thu, Jun 16, 2022 at 10:05:06AM +0200, Alexander Stein wrote:
> > Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> > > The ISP that is integrated in the i.MX8MP uses different bits in the
> > > MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> > > compared to the on in the RK3399. In addition, it adds a new bit for
> > > enabling crop. Add new definitions for these bits for i.MX8MP devices,
> > > and update where they are set.
> > > 
> > > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > > ---
> > >  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
> > >  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
> > >  2 files changed, 12 insertions(+), 2 deletions(-)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> > > 34f4fe09c88d..24ad2ccec2a3 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > @@ -168,6 +168,10 @@
> > >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> > >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> > > 
> > > +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> > > +
> > 
> > Does it make sense to move this kind of information into struct rkisp1_info? 
> > This way you can skip the if (isp_ver == ...) thing.
> 
> Good question. Paul, what do you think ? If it doesn't get moved to the
> structure, I think I'd condition it by the RKISP1_FEATURE_RSZ_CROP
> feature bit instead of a version check, as it seems closely related. I'm
> actually leaning towards the latter.
> 
> > >  /* RSZ_CROP_[XY]_DIR */
> > >  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> > > 08bf3aa8088f..29a31b18a082 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> > > rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> > > RKISP1_CIF_RSZ_CTRL);
> > > 
> > >  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > >  	else
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > 
> > >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
> > >  }

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
@ 2022-06-26 11:40         ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:40 UTC (permalink / raw)
  To: Paul Elder
  Cc: Alexander Stein, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Paul,

Ping

On Sat, Jun 18, 2022 at 02:03:19AM +0300, Laurent Pinchart wrote:
> On Thu, Jun 16, 2022 at 10:05:06AM +0200, Alexander Stein wrote:
> > Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> > > The ISP that is integrated in the i.MX8MP uses different bits in the
> > > MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> > > compared to the on in the RK3399. In addition, it adds a new bit for
> > > enabling crop. Add new definitions for these bits for i.MX8MP devices,
> > > and update where they are set.
> > > 
> > > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > > ---
> > >  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
> > >  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
> > >  2 files changed, 12 insertions(+), 2 deletions(-)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> > > 34f4fe09c88d..24ad2ccec2a3 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > @@ -168,6 +168,10 @@
> > >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> > >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> > > 
> > > +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> > > +
> > 
> > Does it make sense to move this kind of information into struct rkisp1_info? 
> > This way you can skip the if (isp_ver == ...) thing.
> 
> Good question. Paul, what do you think ? If it doesn't get moved to the
> structure, I think I'd condition it by the RKISP1_FEATURE_RSZ_CROP
> feature bit instead of a version check, as it seems closely related. I'm
> actually leaning towards the latter.
> 
> > >  /* RSZ_CROP_[XY]_DIR */
> > >  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> > > 08bf3aa8088f..29a31b18a082 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> > > rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> > > RKISP1_CIF_RSZ_CTRL);
> > > 
> > >  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > >  	else
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > 
> > >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
> > >  }

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-26 11:46     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:46 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:23AM +0900, Paul Elder wrote:
> The ISP version in the i.MX8MP has a set of registers currently not
> handled by the driver for output size configuration. Add a feature flag
> to determine if the ISP requires this, and set the registers based on
> that.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c | 8 ++++++++
>  drivers/media/platform/rockchip/rkisp1/rkisp1-common.h  | 1 +
>  drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c     | 3 ++-
>  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h    | 9 +++++++++
>  4 files changed, 20 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> index 9edaa95fa44c..35cec263c563 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> @@ -420,6 +420,14 @@ static void rkisp1_mp_config(struct rkisp1_capture *cap)
>  	rkisp1_write(rkisp1, cap->config->mi.cr_size_init,
>  		     rkisp1_pixfmt_comp_size(pixm, RKISP1_PLANE_CR));
>  
> +	if (rkisp1->info->features & RKISP1_FEATURE_MAIN_STRIDE) {
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_LLENGTH, pixm->width);
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_WIDTH, pixm->width);
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_HEIGHT, pixm->height);
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_SIZE,
> +			     pixm->width * pixm->height);
> +	}
> +
>  	rkisp1_irq_frame_end_enable(cap);
>  
>  	/* set uv swapping for semiplanar formats */
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index e4f422bed09a..96657e55a5b0 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -112,6 +112,7 @@ enum rkisp1_feature {
>  	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
> +	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index 5abe33f5fed4..d68a805e8b6b 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -505,7 +505,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
>  	.isrs = imx8mp_isp_isrs,
>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>  	.isp_ver = IMX8MP_V10,
> -	.features = RKISP1_FEATURE_RSZ_CROP,
> +	.features = RKISP1_FEATURE_RSZ_CROP
> +		  | RKISP1_FEATURE_MAIN_STRIDE,
>  };
>  
>  static const struct of_device_id rkisp1_of_match[] = {
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> index 1fc54ab22b6d..5c2195019723 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> @@ -1013,6 +1013,15 @@
>  #define RKISP1_CIF_MI_SP_CB_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000140)
>  #define RKISP1_CIF_MI_SP_CR_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000144)
>  #define RKISP1_CIF_MI_XTD_FORMAT_CTRL		(RKISP1_CIF_MI_BASE + 0x00000148)
> +#define RKISP1_CIF_MI_MP_HANDSHAKE_0		(RKISP1_CIF_MI_BASE + 0x0000014C)
> +#define RKISP1_CIF_MI_MP_Y_LLENGTH		(RKISP1_CIF_MI_BASE + 0x00000150)
> +#define RKISP1_CIF_MI_MP_Y_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000154)
> +#define RKISP1_CIF_MI_MP_C_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000158)
> +#define RKISP1_CIF_MI_OUTPUT_ALIGN_FORMAT	(RKISP1_CIF_MI_BASE + 0x0000015C)
> +#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE	(RKISP1_CIF_MI_BASE + 0x00000160)
> +#define RKISP1_CIF_MI_MP_Y_PIC_WIDTH		(RKISP1_CIF_MI_BASE + 0x00000164)
> +#define RKISP1_CIF_MI_MP_Y_PIC_HEIGHT		(RKISP1_CIF_MI_BASE + 0x00000168)
> +#define RKISP1_CIF_MI_MP_Y_PIC_SIZE		(RKISP1_CIF_MI_BASE + 0x0000016C)
>  
>  #define RKISP1_CIF_SMIA_BASE			0x00001A00
>  #define RKISP1_CIF_SMIA_CTRL			(RKISP1_CIF_SMIA_BASE + 0x00000000)

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP
@ 2022-06-26 11:46     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:46 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:23AM +0900, Paul Elder wrote:
> The ISP version in the i.MX8MP has a set of registers currently not
> handled by the driver for output size configuration. Add a feature flag
> to determine if the ISP requires this, and set the registers based on
> that.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> ---
>  drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c | 8 ++++++++
>  drivers/media/platform/rockchip/rkisp1/rkisp1-common.h  | 1 +
>  drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c     | 3 ++-
>  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h    | 9 +++++++++
>  4 files changed, 20 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> index 9edaa95fa44c..35cec263c563 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> @@ -420,6 +420,14 @@ static void rkisp1_mp_config(struct rkisp1_capture *cap)
>  	rkisp1_write(rkisp1, cap->config->mi.cr_size_init,
>  		     rkisp1_pixfmt_comp_size(pixm, RKISP1_PLANE_CR));
>  
> +	if (rkisp1->info->features & RKISP1_FEATURE_MAIN_STRIDE) {
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_LLENGTH, pixm->width);
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_WIDTH, pixm->width);
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_HEIGHT, pixm->height);
> +		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_SIZE,
> +			     pixm->width * pixm->height);
> +	}
> +
>  	rkisp1_irq_frame_end_enable(cap);
>  
>  	/* set uv swapping for semiplanar formats */
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index e4f422bed09a..96657e55a5b0 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -112,6 +112,7 @@ enum rkisp1_feature {
>  	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
> +	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index 5abe33f5fed4..d68a805e8b6b 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -505,7 +505,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
>  	.isrs = imx8mp_isp_isrs,
>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>  	.isp_ver = IMX8MP_V10,
> -	.features = RKISP1_FEATURE_RSZ_CROP,
> +	.features = RKISP1_FEATURE_RSZ_CROP
> +		  | RKISP1_FEATURE_MAIN_STRIDE,
>  };
>  
>  static const struct of_device_id rkisp1_of_match[] = {
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> index 1fc54ab22b6d..5c2195019723 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> @@ -1013,6 +1013,15 @@
>  #define RKISP1_CIF_MI_SP_CB_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000140)
>  #define RKISP1_CIF_MI_SP_CR_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000144)
>  #define RKISP1_CIF_MI_XTD_FORMAT_CTRL		(RKISP1_CIF_MI_BASE + 0x00000148)
> +#define RKISP1_CIF_MI_MP_HANDSHAKE_0		(RKISP1_CIF_MI_BASE + 0x0000014C)
> +#define RKISP1_CIF_MI_MP_Y_LLENGTH		(RKISP1_CIF_MI_BASE + 0x00000150)
> +#define RKISP1_CIF_MI_MP_Y_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000154)
> +#define RKISP1_CIF_MI_MP_C_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000158)
> +#define RKISP1_CIF_MI_OUTPUT_ALIGN_FORMAT	(RKISP1_CIF_MI_BASE + 0x0000015C)
> +#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE	(RKISP1_CIF_MI_BASE + 0x00000160)
> +#define RKISP1_CIF_MI_MP_Y_PIC_WIDTH		(RKISP1_CIF_MI_BASE + 0x00000164)
> +#define RKISP1_CIF_MI_MP_Y_PIC_HEIGHT		(RKISP1_CIF_MI_BASE + 0x00000168)
> +#define RKISP1_CIF_MI_MP_Y_PIC_SIZE		(RKISP1_CIF_MI_BASE + 0x0000016C)
>  
>  #define RKISP1_CIF_SMIA_BASE			0x00001A00
>  #define RKISP1_CIF_SMIA_CTRL			(RKISP1_CIF_SMIA_BASE + 0x00000000)

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
  2022-06-14 19:11   ` Paul Elder
@ 2022-06-26 11:59     ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:59 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:22AM +0900, Paul Elder wrote:
> The ISP version in the i.MX8MP has a separate set of registers for crop
> that is currently not handled. Add a feature flag to determine which
> type of crop the ISP supports and set the crop registers based on that.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
>  .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
>  .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
>  5 files changed, 46 insertions(+), 5 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 667fca0fef95..e4f422bed09a 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
>   */
>  enum rkisp1_feature {
>  	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
> +	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> +	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> index 02854e8ea1a4..753abd024ce7 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> @@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
>  		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
>  		{ /* Sentinel */ },
>  	};
> +	static const struct rkisp1_debug_register crop_registers[] = {
> +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
> +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
> +		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
> +		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
> +		{ /* Sentinel */ },
> +	};
>  	struct rkisp1_resizer *rsz = m->private;
>  
> -	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> +	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
> +		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
> +				       crop_registers);
> +
> +	return 0;
>  }
>  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
>  
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index a4496ee2e9b4..5abe33f5fed4 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
>  	.isrs = px30_isp_isrs,
>  	.isr_size = ARRAY_SIZE(px30_isp_isrs),
>  	.isp_ver = RKISP1_V12,
> -	.features = RKISP1_FEATURE_MIPI_CSI2,
> +	.features = RKISP1_FEATURE_MIPI_CSI2
> +		  | RKISP1_FEATURE_DUAL_CROP,
>  };
>  
>  static const char * const rk3399_isp_clks[] = {
> @@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
>  	.isrs = rk3399_isp_isrs,
>  	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
>  	.isp_ver = RKISP1_V10,
> -	.features = RKISP1_FEATURE_MIPI_CSI2,
> +	.features = RKISP1_FEATURE_MIPI_CSI2
> +		  | RKISP1_FEATURE_DUAL_CROP,
>  };
>  
>  static const char * const imx8mp_isp_clks[] = {
> @@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
>  	.isrs = imx8mp_isp_isrs,
>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>  	.isp_ver = IMX8MP_V10,
> +	.features = RKISP1_FEATURE_RSZ_CROP,
>  };
>  
>  static const struct of_device_id rkisp1_of_match[] = {
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> index dd3e6c38be67..1fc54ab22b6d 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> @@ -168,6 +168,9 @@
>  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
>  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
>  
> +/* RSZ_CROP_[XY]_DIR */
> +#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> +
>  /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
>  #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
>  #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
> @@ -926,6 +929,12 @@
>  #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
>  #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
>  #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
> +#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
> +#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
> +#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
> +#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
> +#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
> +#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
>  
>  #define RKISP1_CIF_MI_BASE			0x00001400
>  #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> index f4caa8f684aa..08bf3aa8088f 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> @@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
>  {
>  	u32 ratio, rsz_ctrl = 0;
>  	unsigned int i;
> +	u32 val;
>  
>  	/* No phase offset */
>  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
> @@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
>  
>  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
>  
> +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
> +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
> +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
> +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
> +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
> +
> +		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
> +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
> +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;

Shouldn't this depend on the input and output formats of the resizer ?

> +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
> +	}
> +
>  	rkisp1_rsz_update_shadow(rsz, when);
>  }
>  
> @@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
>  	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
>  
>  	if (!enable) {
> -		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> +		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> +			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
>  		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
>  		return 0;
>  	}
> @@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
>  
>  	mutex_lock(&rsz->ops_lock);
>  	rkisp1_rsz_config(rsz, when);
> -	rkisp1_dcrop_config(rsz);
> +	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> +		rkisp1_dcrop_config(rsz);
>  
>  	mutex_unlock(&rsz->ops_lock);
>  	return 0;

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
@ 2022-06-26 11:59     ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-06-26 11:59 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Paul,

Thank you for the patch.

On Wed, Jun 15, 2022 at 04:11:22AM +0900, Paul Elder wrote:
> The ISP version in the i.MX8MP has a separate set of registers for crop
> that is currently not handled. Add a feature flag to determine which
> type of crop the ISP supports and set the crop registers based on that.
> 
> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> ---
>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
>  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
>  .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
>  .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
>  5 files changed, 46 insertions(+), 5 deletions(-)
> 
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> index 667fca0fef95..e4f422bed09a 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> @@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
>   */
>  enum rkisp1_feature {
>  	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
> +	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> +	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>  };
>  
>  /*
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> index 02854e8ea1a4..753abd024ce7 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> @@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
>  		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
>  		{ /* Sentinel */ },
>  	};
> +	static const struct rkisp1_debug_register crop_registers[] = {
> +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
> +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
> +		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
> +		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
> +		{ /* Sentinel */ },
> +	};
>  	struct rkisp1_resizer *rsz = m->private;
>  
> -	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> +	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
> +		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
> +				       crop_registers);
> +
> +	return 0;
>  }
>  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
>  
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> index a4496ee2e9b4..5abe33f5fed4 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> @@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
>  	.isrs = px30_isp_isrs,
>  	.isr_size = ARRAY_SIZE(px30_isp_isrs),
>  	.isp_ver = RKISP1_V12,
> -	.features = RKISP1_FEATURE_MIPI_CSI2,
> +	.features = RKISP1_FEATURE_MIPI_CSI2
> +		  | RKISP1_FEATURE_DUAL_CROP,
>  };
>  
>  static const char * const rk3399_isp_clks[] = {
> @@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
>  	.isrs = rk3399_isp_isrs,
>  	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
>  	.isp_ver = RKISP1_V10,
> -	.features = RKISP1_FEATURE_MIPI_CSI2,
> +	.features = RKISP1_FEATURE_MIPI_CSI2
> +		  | RKISP1_FEATURE_DUAL_CROP,
>  };
>  
>  static const char * const imx8mp_isp_clks[] = {
> @@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
>  	.isrs = imx8mp_isp_isrs,
>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>  	.isp_ver = IMX8MP_V10,
> +	.features = RKISP1_FEATURE_RSZ_CROP,
>  };
>  
>  static const struct of_device_id rkisp1_of_match[] = {
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> index dd3e6c38be67..1fc54ab22b6d 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> @@ -168,6 +168,9 @@
>  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
>  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
>  
> +/* RSZ_CROP_[XY]_DIR */
> +#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> +
>  /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
>  #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
>  #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
> @@ -926,6 +929,12 @@
>  #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
>  #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
>  #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
> +#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
> +#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
> +#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
> +#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
> +#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
> +#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
>  
>  #define RKISP1_CIF_MI_BASE			0x00001400
>  #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> index f4caa8f684aa..08bf3aa8088f 100644
> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> @@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
>  {
>  	u32 ratio, rsz_ctrl = 0;
>  	unsigned int i;
> +	u32 val;
>  
>  	/* No phase offset */
>  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
> @@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
>  
>  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
>  
> +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
> +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
> +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
> +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
> +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
> +
> +		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
> +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
> +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;

Shouldn't this depend on the input and output formats of the resizer ?

> +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
> +	}
> +
>  	rkisp1_rsz_update_shadow(rsz, when);
>  }
>  
> @@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
>  	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
>  
>  	if (!enable) {
> -		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> +		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> +			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
>  		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
>  		return 0;
>  	}
> @@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
>  
>  	mutex_lock(&rsz->ops_lock);
>  	rkisp1_rsz_config(rsz, when);
> -	rkisp1_dcrop_config(rsz);
> +	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> +		rkisp1_dcrop_config(rsz);
>  
>  	mutex_unlock(&rsz->ops_lock);
>  	return 0;

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
  2022-06-24 14:47       ` Laurent Pinchart
@ 2022-06-30 21:28         ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-30 21:28 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 24.06.2022 17:47, Laurent Pinchart wrote:
>Hi Dafna,
>
>On Fri, Jun 24, 2022 at 05:34:00PM +0300, Dafna Hirschfeld wrote:
>> On 15.06.2022 04:10, Paul Elder wrote:
>> > To make it possible to use the rkisp1_info after probe time (for
>> > instance to make code conditional on the ISP version), save it in the
>> > main rkisp1_device structure. To achieve this, also move the info
>> > structure into the common header, and document it.
>> >
>> > While at it, drop a NULL check in rkisp1_probe() for the match data as
>> > it can't happen.
>> >
>> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>> > ---
>> >  .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
>> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
>> >  2 files changed, 25 insertions(+), 12 deletions(-)
>> >
>> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> > index a67fe7b1dfa1..50d31a254b03 100644
>> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> > @@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
>> >  	RKISP1_ISP_PAD_MAX
>> >  };
>> >
>> > +/*
>> > + * struct rkisp1_info - Model-specific ISP Information
>> > + *
>> > + * @clks: array of ISP clock names
>> > + * @clk_size: number of entries in the @clks array
>> > + * @isrs: array of ISP interrupt descriptors
>> > + * @isr_size: number of entires in the @isrs array
>> > + * @isp_ver: ISP version
>> > + *
>> > + * This structure contains information about the ISP specific to a particular
>> > + * ISP model, version, or integration in a particular SoC.
>> > + */
>> > +struct rkisp1_info {
>> > +	const char * const *clks;
>> > +	unsigned int clk_size;
>> > +	const struct rkisp1_isr_data *isrs;
>> > +	unsigned int isr_size;
>> > +	enum rkisp1_cif_isp_version isp_ver;
>> > +};
>> > +
>> >  /*
>> >   * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
>> >   *				of the v4l2-async API
>> > @@ -395,6 +415,7 @@ struct rkisp1_debug {
>> >   * @pipe:	   media pipeline
>> >   * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
>> >   * @debug:	   debug params to be exposed on debugfs
>> > + * @info:	   version-specific ISP information
>> >   */
>> >  struct rkisp1_device {
>> >  	void __iomem *base_addr;
>> > @@ -413,6 +434,7 @@ struct rkisp1_device {
>> >  	struct media_pipeline pipe;
>> >  	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
>> >  	struct rkisp1_debug debug;
>> > +	const struct rkisp1_info *info;
>> >  };
>> >
>> >  /*
>> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> > index 258980ef4783..39ae35074062 100644
>> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> > @@ -105,14 +105,6 @@ struct rkisp1_isr_data {
>> >  	irqreturn_t (*isr)(int irq, void *ctx);
>> >  };
>> >
>> > -struct rkisp1_info {
>> > -	const char * const *clks;
>> > -	unsigned int clk_size;
>> > -	const struct rkisp1_isr_data *isrs;
>> > -	unsigned int isr_size;
>> > -	enum rkisp1_cif_isp_version isp_ver;
>> > -};
>> > -
>> >  /* ----------------------------------------------------------------------------
>> >   * Sensor DT bindings
>> >   */
>> > @@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
>> >  	int ret, irq;
>> >  	u32 cif_id;
>> >
>> > -	info = of_device_get_match_data(&pdev->dev);
>> > -	if (!info)
>> > -		return -ENODEV;
>> > -
>> >  	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
>> >  	if (!rkisp1)
>> >  		return -ENOMEM;
>> >
>> > +	info = of_device_get_match_data(dev);
>>
>> Why did you omit the check 'if(!info)'?
>
>Because it can't happen. The probe() function is only called if the
>platform device matches one of the of_device_id, so
>of_device_get_match_data() can't return NULL.
>

I see now it is also written in the commit log,

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>> > +	rkisp1->info = info;
>> > +
>> >  	dev_set_drvdata(dev, rkisp1);
>> >  	rkisp1->dev = dev;
>> >
>
>-- 
>Regards,
>
>Laurent Pinchart
>
>_______________________________________________
>Linux-rockchip mailing list
>Linux-rockchip@lists.infradead.org
>http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device
@ 2022-06-30 21:28         ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-30 21:28 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 24.06.2022 17:47, Laurent Pinchart wrote:
>Hi Dafna,
>
>On Fri, Jun 24, 2022 at 05:34:00PM +0300, Dafna Hirschfeld wrote:
>> On 15.06.2022 04:10, Paul Elder wrote:
>> > To make it possible to use the rkisp1_info after probe time (for
>> > instance to make code conditional on the ISP version), save it in the
>> > main rkisp1_device structure. To achieve this, also move the info
>> > structure into the common header, and document it.
>> >
>> > While at it, drop a NULL check in rkisp1_probe() for the match data as
>> > it can't happen.
>> >
>> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>> > ---
>> >  .../platform/rockchip/rkisp1/rkisp1-common.h  | 22 +++++++++++++++++++
>> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 15 +++----------
>> >  2 files changed, 25 insertions(+), 12 deletions(-)
>> >
>> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> > index a67fe7b1dfa1..50d31a254b03 100644
>> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> > @@ -91,6 +91,26 @@ enum rkisp1_isp_pad {
>> >  	RKISP1_ISP_PAD_MAX
>> >  };
>> >
>> > +/*
>> > + * struct rkisp1_info - Model-specific ISP Information
>> > + *
>> > + * @clks: array of ISP clock names
>> > + * @clk_size: number of entries in the @clks array
>> > + * @isrs: array of ISP interrupt descriptors
>> > + * @isr_size: number of entires in the @isrs array
>> > + * @isp_ver: ISP version
>> > + *
>> > + * This structure contains information about the ISP specific to a particular
>> > + * ISP model, version, or integration in a particular SoC.
>> > + */
>> > +struct rkisp1_info {
>> > +	const char * const *clks;
>> > +	unsigned int clk_size;
>> > +	const struct rkisp1_isr_data *isrs;
>> > +	unsigned int isr_size;
>> > +	enum rkisp1_cif_isp_version isp_ver;
>> > +};
>> > +
>> >  /*
>> >   * struct rkisp1_sensor_async - A container for the v4l2_async_subdev to add to the notifier
>> >   *				of the v4l2-async API
>> > @@ -395,6 +415,7 @@ struct rkisp1_debug {
>> >   * @pipe:	   media pipeline
>> >   * @stream_lock:   serializes {start/stop}_streaming callbacks between the capture devices.
>> >   * @debug:	   debug params to be exposed on debugfs
>> > + * @info:	   version-specific ISP information
>> >   */
>> >  struct rkisp1_device {
>> >  	void __iomem *base_addr;
>> > @@ -413,6 +434,7 @@ struct rkisp1_device {
>> >  	struct media_pipeline pipe;
>> >  	struct mutex stream_lock; /* serialize {start/stop}_streaming cb between capture devices */
>> >  	struct rkisp1_debug debug;
>> > +	const struct rkisp1_info *info;
>> >  };
>> >
>> >  /*
>> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> > index 258980ef4783..39ae35074062 100644
>> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> > @@ -105,14 +105,6 @@ struct rkisp1_isr_data {
>> >  	irqreturn_t (*isr)(int irq, void *ctx);
>> >  };
>> >
>> > -struct rkisp1_info {
>> > -	const char * const *clks;
>> > -	unsigned int clk_size;
>> > -	const struct rkisp1_isr_data *isrs;
>> > -	unsigned int isr_size;
>> > -	enum rkisp1_cif_isp_version isp_ver;
>> > -};
>> > -
>> >  /* ----------------------------------------------------------------------------
>> >   * Sensor DT bindings
>> >   */
>> > @@ -469,14 +461,13 @@ static int rkisp1_probe(struct platform_device *pdev)
>> >  	int ret, irq;
>> >  	u32 cif_id;
>> >
>> > -	info = of_device_get_match_data(&pdev->dev);
>> > -	if (!info)
>> > -		return -ENODEV;
>> > -
>> >  	rkisp1 = devm_kzalloc(dev, sizeof(*rkisp1), GFP_KERNEL);
>> >  	if (!rkisp1)
>> >  		return -ENOMEM;
>> >
>> > +	info = of_device_get_match_data(dev);
>>
>> Why did you omit the check 'if(!info)'?
>
>Because it can't happen. The probe() function is only called if the
>platform device matches one of the of_device_id, so
>of_device_get_match_data() can't return NULL.
>

I see now it is also written in the commit log,

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>> > +	rkisp1->info = info;
>> > +
>> >  	dev_set_drvdata(dev, rkisp1);
>> >  	rkisp1->dev = dev;
>> >
>
>-- 
>Regards,
>
>Laurent Pinchart
>
>_______________________________________________
>Linux-rockchip mailing list
>Linux-rockchip@lists.infradead.org
>http://lists.infradead.org/mailman/listinfo/linux-rockchip

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
  2022-06-14 19:10   ` Paul Elder
@ 2022-06-30 21:57     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-30 21:57 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The active_sensor field of the rkisp1_device structure points to the ASD
>data for the active source. The source may however not be a sensor, so
>the naming is a bit confusing. Furthermore, the driver doesn't need to
>access the full ASD from the active_sensor field, only the subdev
>pointer is needed, when stopping streaming.
>
>Rename the field to source, and turn it into a v4l2_subdev pointer.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  4 +--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 27 +++++++++----------
> 2 files changed, 14 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index dbf1baca623a..7a6f55a31bb0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -419,7 +419,7 @@ struct rkisp1_debug {
>  * @v4l2_dev:	   v4l2_device variable
>  * @media_dev:	   media_device variable
>  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
>- * @active_sensor: sensor in-use, set when streaming on
>+ * @source:        source subdev in-use, set when starting streaming
>  * @csi:	   internal CSI-2 receiver
>  * @isp:	   ISP sub-device
>  * @resizer_devs:  resizer sub-devices
>@@ -439,7 +439,7 @@ struct rkisp1_device {
> 	struct v4l2_device v4l2_dev;
> 	struct media_device media_dev;
> 	struct v4l2_async_notifier notifier;
>-	struct rkisp1_sensor_async *active_sensor;
>+	struct v4l2_subdev *source;
> 	struct rkisp1_csi csi;
> 	struct rkisp1_isp isp;
> 	struct rkisp1_resizer resizer_devs[2];
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f6d1c93dd99d..4f12fc0b7694 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -58,7 +58,7 @@
>  * Helpers
>  */
>
>-static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
>+static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
> 	struct media_entity *sensor_me;
>@@ -749,12 +749,11 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = &rkisp1->isp;
>-	struct v4l2_subdev *sensor_sd;
>+	struct rkisp1_sensor_async *asd;
> 	int ret;
>
> 	if (!enable) {
>-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-				 false);
>+		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>
> 		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(rkisp1);
>@@ -762,35 +761,33 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return 0;
> 	}
>
>-	sensor_sd = rkisp1_get_remote_sensor(sd);
>-	if (!sensor_sd) {
>-		dev_warn(rkisp1->dev, "No link between isp and sensor\n");
>+	rkisp1->source = rkisp1_get_remote_source(sd);
>+	if (!rkisp1->source) {
>+		dev_warn(rkisp1->dev, "No link between isp and source\n");
> 		return -ENODEV;
> 	}
>
>-	rkisp1->active_sensor = container_of(sensor_sd->asd,
>-					     struct rkisp1_sensor_async, asd);
>+	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
>+			   asd);
>
>-	if (rkisp1->active_sensor->mbus_type != V4L2_MBUS_CSI2_DPHY)
>+	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> 		return -EINVAL;
>
> 	rkisp1->isp.frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
>-				rkisp1->active_sensor->mbus_flags);
>+	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
> 	rkisp1_isp_start(rkisp1);
>
>-	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
>+	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
> 	}
>
>-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-			       true);
>+	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		rkisp1_csi_stop(&rkisp1->csi);
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
@ 2022-06-30 21:57     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-06-30 21:57 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>The active_sensor field of the rkisp1_device structure points to the ASD
>data for the active source. The source may however not be a sensor, so
>the naming is a bit confusing. Furthermore, the driver doesn't need to
>access the full ASD from the active_sensor field, only the subdev
>pointer is needed, when stopping streaming.
>
>Rename the field to source, and turn it into a v4l2_subdev pointer.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  4 +--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 27 +++++++++----------
> 2 files changed, 14 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index dbf1baca623a..7a6f55a31bb0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -419,7 +419,7 @@ struct rkisp1_debug {
>  * @v4l2_dev:	   v4l2_device variable
>  * @media_dev:	   media_device variable
>  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
>- * @active_sensor: sensor in-use, set when streaming on
>+ * @source:        source subdev in-use, set when starting streaming
>  * @csi:	   internal CSI-2 receiver
>  * @isp:	   ISP sub-device
>  * @resizer_devs:  resizer sub-devices
>@@ -439,7 +439,7 @@ struct rkisp1_device {
> 	struct v4l2_device v4l2_dev;
> 	struct media_device media_dev;
> 	struct v4l2_async_notifier notifier;
>-	struct rkisp1_sensor_async *active_sensor;
>+	struct v4l2_subdev *source;
> 	struct rkisp1_csi csi;
> 	struct rkisp1_isp isp;
> 	struct rkisp1_resizer resizer_devs[2];
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f6d1c93dd99d..4f12fc0b7694 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -58,7 +58,7 @@
>  * Helpers
>  */
>
>-static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
>+static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
> 	struct media_entity *sensor_me;
>@@ -749,12 +749,11 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = &rkisp1->isp;
>-	struct v4l2_subdev *sensor_sd;
>+	struct rkisp1_sensor_async *asd;
> 	int ret;
>
> 	if (!enable) {
>-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-				 false);
>+		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>
> 		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(rkisp1);
>@@ -762,35 +761,33 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return 0;
> 	}
>
>-	sensor_sd = rkisp1_get_remote_sensor(sd);
>-	if (!sensor_sd) {
>-		dev_warn(rkisp1->dev, "No link between isp and sensor\n");
>+	rkisp1->source = rkisp1_get_remote_source(sd);
>+	if (!rkisp1->source) {
>+		dev_warn(rkisp1->dev, "No link between isp and source\n");
> 		return -ENODEV;
> 	}
>
>-	rkisp1->active_sensor = container_of(sensor_sd->asd,
>-					     struct rkisp1_sensor_async, asd);
>+	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
>+			   asd);
>
>-	if (rkisp1->active_sensor->mbus_type != V4L2_MBUS_CSI2_DPHY)
>+	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> 		return -EINVAL;
>
> 	rkisp1->isp.frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
>-				rkisp1->active_sensor->mbus_flags);
>+	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
> 	rkisp1_isp_start(rkisp1);
>
>-	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
>+	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
> 	}
>
>-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-			       true);
>+	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		rkisp1_csi_stop(&rkisp1->csi);
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time
  2022-06-14 19:10   ` Paul Elder
@ 2022-07-01  4:36     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  4:36 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>When a sensor is bound, its source pad is retrieved in the .bound()
>operation with a call to media_entity_get_fwnode_pad(). The function
>should be called with the source endpoint fwnode of the sensor, but is
>instead called with the sensor's device fwnode.
>
>Fix this, which involves storing a reference to the source endpoint
>fwnode in the rkisp1_sensor_async structure, and thus implementing the
>subdev notifier .destroy() operation to release the reference.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 28 ++++++++++++++++---
> 2 files changed, 26 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index ba11baf75fa9..60c5462e1746 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -117,6 +117,7 @@ struct rkisp1_info {
>  *
>  * @asd:		async_subdev variable for the sensor
>  * @index:		index of the sensor (counting sensor found in DT)
>+ * @source_ep:		fwnode for the sensor source endpoint
>  * @lanes:		number of lanes
>  * @mbus_type:		type of bus (currently only CSI2 is supported)
>  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
>@@ -127,6 +128,7 @@ struct rkisp1_info {
> struct rkisp1_sensor_async {
> 	struct v4l2_async_subdev asd;
> 	unsigned int index;
>+	struct fwnode_handle *source_ep;
> 	unsigned int lanes;
> 	enum v4l2_mbus_type mbus_type;
> 	unsigned int mbus_flags;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 386c1c17aec2..0f3e45cdbf2a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -138,7 +138,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 	phy_init(s_asd->dphy);
>
> 	/* Create the link to the sensor. */
>-	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
>+	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> 						 MEDIA_PAD_FL_SOURCE);
> 	if (source_pad < 0) {
> 		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
>@@ -170,10 +170,19 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> 	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
> }
>
>+static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
>+{
>+	struct rkisp1_sensor_async *rk_asd =
>+		container_of(asd, struct rkisp1_sensor_async, asd);
>+
>+	fwnode_handle_put(rk_asd->source_ep);
>+}
>+
> static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> 	.bound = rkisp1_subdev_notifier_bound,
> 	.unbind = rkisp1_subdev_notifier_unbind,
> 	.complete = rkisp1_subdev_notifier_complete,
>+	.destroy = rkisp1_subdev_notifier_destroy,
> };
>
> static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>@@ -190,6 +199,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> 			.bus_type = V4L2_MBUS_CSI2_DPHY
> 		};
> 		struct rkisp1_sensor_async *rk_asd;
>+		struct fwnode_handle *source = NULL;
> 		struct fwnode_handle *ep;
>
> 		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
>@@ -202,15 +212,24 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> 		if (ret)
> 			goto err_parse;
>
>-		rk_asd = v4l2_async_nf_add_fwnode_remote(ntf, ep,
>-							 struct
>-							 rkisp1_sensor_async);
>+		source = fwnode_graph_get_remote_endpoint(ep);
>+		if (!source) {
>+			dev_err(rkisp1->dev,
>+				"endpoint %pfw has no remote endpoint\n",
>+				ep);
>+			ret = -ENODEV;
>+			goto err_parse;
>+		}
>+
>+		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
>+						  struct rkisp1_sensor_async);
> 		if (IS_ERR(rk_asd)) {
> 			ret = PTR_ERR(rk_asd);
> 			goto err_parse;
> 		}
>
> 		rk_asd->index = index++;
>+		rk_asd->source_ep = source;

here do 'source = NULL', see reason below

> 		rk_asd->mbus_type = vep.bus_type;
> 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
> 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
>@@ -225,6 +244,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> 		continue;
> err_parse:
> 		fwnode_handle_put(ep);
>+		fwnode_handle_put(source);

if v4l2_fwnode_endpoint_parse fails then here you put the source of previous iteration

thanks,
Dafna

> 		v4l2_async_nf_cleanup(ntf);
> 		return ret;
> 	}
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time
@ 2022-07-01  4:36     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  4:36 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>When a sensor is bound, its source pad is retrieved in the .bound()
>operation with a call to media_entity_get_fwnode_pad(). The function
>should be called with the source endpoint fwnode of the sensor, but is
>instead called with the sensor's device fwnode.
>
>Fix this, which involves storing a reference to the source endpoint
>fwnode in the rkisp1_sensor_async structure, and thus implementing the
>subdev notifier .destroy() operation to release the reference.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> .../platform/rockchip/rkisp1/rkisp1-dev.c     | 28 ++++++++++++++++---
> 2 files changed, 26 insertions(+), 4 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index ba11baf75fa9..60c5462e1746 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -117,6 +117,7 @@ struct rkisp1_info {
>  *
>  * @asd:		async_subdev variable for the sensor
>  * @index:		index of the sensor (counting sensor found in DT)
>+ * @source_ep:		fwnode for the sensor source endpoint
>  * @lanes:		number of lanes
>  * @mbus_type:		type of bus (currently only CSI2 is supported)
>  * @mbus_flags:		media bus (V4L2_MBUS_*) flags
>@@ -127,6 +128,7 @@ struct rkisp1_info {
> struct rkisp1_sensor_async {
> 	struct v4l2_async_subdev asd;
> 	unsigned int index;
>+	struct fwnode_handle *source_ep;
> 	unsigned int lanes;
> 	enum v4l2_mbus_type mbus_type;
> 	unsigned int mbus_flags;
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 386c1c17aec2..0f3e45cdbf2a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -138,7 +138,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> 	phy_init(s_asd->dphy);
>
> 	/* Create the link to the sensor. */
>-	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
>+	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> 						 MEDIA_PAD_FL_SOURCE);
> 	if (source_pad < 0) {
> 		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
>@@ -170,10 +170,19 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> 	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
> }
>
>+static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
>+{
>+	struct rkisp1_sensor_async *rk_asd =
>+		container_of(asd, struct rkisp1_sensor_async, asd);
>+
>+	fwnode_handle_put(rk_asd->source_ep);
>+}
>+
> static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> 	.bound = rkisp1_subdev_notifier_bound,
> 	.unbind = rkisp1_subdev_notifier_unbind,
> 	.complete = rkisp1_subdev_notifier_complete,
>+	.destroy = rkisp1_subdev_notifier_destroy,
> };
>
> static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
>@@ -190,6 +199,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> 			.bus_type = V4L2_MBUS_CSI2_DPHY
> 		};
> 		struct rkisp1_sensor_async *rk_asd;
>+		struct fwnode_handle *source = NULL;
> 		struct fwnode_handle *ep;
>
> 		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
>@@ -202,15 +212,24 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> 		if (ret)
> 			goto err_parse;
>
>-		rk_asd = v4l2_async_nf_add_fwnode_remote(ntf, ep,
>-							 struct
>-							 rkisp1_sensor_async);
>+		source = fwnode_graph_get_remote_endpoint(ep);
>+		if (!source) {
>+			dev_err(rkisp1->dev,
>+				"endpoint %pfw has no remote endpoint\n",
>+				ep);
>+			ret = -ENODEV;
>+			goto err_parse;
>+		}
>+
>+		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
>+						  struct rkisp1_sensor_async);
> 		if (IS_ERR(rk_asd)) {
> 			ret = PTR_ERR(rk_asd);
> 			goto err_parse;
> 		}
>
> 		rk_asd->index = index++;
>+		rk_asd->source_ep = source;

here do 'source = NULL', see reason below

> 		rk_asd->mbus_type = vep.bus_type;
> 		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
> 		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
>@@ -225,6 +244,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> 		continue;
> err_parse:
> 		fwnode_handle_put(ep);
>+		fwnode_handle_put(source);

if v4l2_fwnode_endpoint_parse fails then here you put the source of previous iteration

thanks,
Dafna

> 		v4l2_async_nf_cleanup(ntf);
> 		return ret;
> 	}
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
  2022-06-14 19:10   ` Paul Elder
@ 2022-07-01  4:42     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  4:42 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>
>The active_sensor field of the rkisp1_device structure points to the ASD
>data for the active source. The source may however not be a sensor, so
>the naming is a bit confusing. Furthermore, the driver doesn't need to
>access the full ASD from the active_sensor field, only the subdev
>pointer is needed, when stopping streaming.
>
>Rename the field to source, and turn it into a v4l2_subdev pointer.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  4 +--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 27 +++++++++----------
> 2 files changed, 14 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index dbf1baca623a..7a6f55a31bb0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -419,7 +419,7 @@ struct rkisp1_debug {
>  * @v4l2_dev:	   v4l2_device variable
>  * @media_dev:	   media_device variable
>  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
>- * @active_sensor: sensor in-use, set when streaming on
>+ * @source:        source subdev in-use, set when starting streaming
>  * @csi:	   internal CSI-2 receiver
>  * @isp:	   ISP sub-device
>  * @resizer_devs:  resizer sub-devices
>@@ -439,7 +439,7 @@ struct rkisp1_device {
> 	struct v4l2_device v4l2_dev;
> 	struct media_device media_dev;
> 	struct v4l2_async_notifier notifier;
>-	struct rkisp1_sensor_async *active_sensor;
>+	struct v4l2_subdev *source;
> 	struct rkisp1_csi csi;
> 	struct rkisp1_isp isp;
> 	struct rkisp1_resizer resizer_devs[2];
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f6d1c93dd99d..4f12fc0b7694 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -58,7 +58,7 @@
>  * Helpers
>  */
>
>-static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
>+static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
> 	struct media_entity *sensor_me;
>@@ -749,12 +749,11 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = &rkisp1->isp;
>-	struct v4l2_subdev *sensor_sd;
>+	struct rkisp1_sensor_async *asd;
> 	int ret;
>
> 	if (!enable) {
>-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-				 false);
>+		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>
> 		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(rkisp1);
>@@ -762,35 +761,33 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return 0;
> 	}
>
>-	sensor_sd = rkisp1_get_remote_sensor(sd);
>-	if (!sensor_sd) {
>-		dev_warn(rkisp1->dev, "No link between isp and sensor\n");
>+	rkisp1->source = rkisp1_get_remote_source(sd);
>+	if (!rkisp1->source) {
>+		dev_warn(rkisp1->dev, "No link between isp and source\n");
> 		return -ENODEV;
> 	}
>
>-	rkisp1->active_sensor = container_of(sensor_sd->asd,
>-					     struct rkisp1_sensor_async, asd);
>+	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
>+			   asd);
>
>-	if (rkisp1->active_sensor->mbus_type != V4L2_MBUS_CSI2_DPHY)
>+	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> 		return -EINVAL;
>
> 	rkisp1->isp.frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
>-				rkisp1->active_sensor->mbus_flags);
>+	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
> 	rkisp1_isp_start(rkisp1);
>
>-	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
>+	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
> 	}
>
>-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-			       true);
>+	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		rkisp1_csi_stop(&rkisp1->csi);
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source
@ 2022-07-01  4:42     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  4:42 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, Laurent Pinchart, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:10, Paul Elder wrote:
>From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

Reviewed-by: Dafna Hirschfeld <dafna@fastmail.com>

>
>The active_sensor field of the rkisp1_device structure points to the ASD
>data for the active source. The source may however not be a sensor, so
>the naming is a bit confusing. Furthermore, the driver doesn't need to
>access the full ASD from the active_sensor field, only the subdev
>pointer is needed, when stopping streaming.
>
>Rename the field to source, and turn it into a v4l2_subdev pointer.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  4 +--
> .../platform/rockchip/rkisp1/rkisp1-isp.c     | 27 +++++++++----------
> 2 files changed, 14 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index dbf1baca623a..7a6f55a31bb0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -419,7 +419,7 @@ struct rkisp1_debug {
>  * @v4l2_dev:	   v4l2_device variable
>  * @media_dev:	   media_device variable
>  * @notifier:	   a notifier to register on the v4l2-async API to be notified on the sensor
>- * @active_sensor: sensor in-use, set when streaming on
>+ * @source:        source subdev in-use, set when starting streaming
>  * @csi:	   internal CSI-2 receiver
>  * @isp:	   ISP sub-device
>  * @resizer_devs:  resizer sub-devices
>@@ -439,7 +439,7 @@ struct rkisp1_device {
> 	struct v4l2_device v4l2_dev;
> 	struct media_device media_dev;
> 	struct v4l2_async_notifier notifier;
>-	struct rkisp1_sensor_async *active_sensor;
>+	struct v4l2_subdev *source;
> 	struct rkisp1_csi csi;
> 	struct rkisp1_isp isp;
> 	struct rkisp1_resizer resizer_devs[2];
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>index f6d1c93dd99d..4f12fc0b7694 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-isp.c
>@@ -58,7 +58,7 @@
>  * Helpers
>  */
>
>-static struct v4l2_subdev *rkisp1_get_remote_sensor(struct v4l2_subdev *sd)
>+static struct v4l2_subdev *rkisp1_get_remote_source(struct v4l2_subdev *sd)
> {
> 	struct media_pad *local, *remote;
> 	struct media_entity *sensor_me;
>@@ -749,12 +749,11 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 	struct rkisp1_device *rkisp1 =
> 		container_of(sd->v4l2_dev, struct rkisp1_device, v4l2_dev);
> 	struct rkisp1_isp *isp = &rkisp1->isp;
>-	struct v4l2_subdev *sensor_sd;
>+	struct rkisp1_sensor_async *asd;
> 	int ret;
>
> 	if (!enable) {
>-		v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-				 false);
>+		v4l2_subdev_call(rkisp1->source, video, s_stream, false);
>
> 		rkisp1_csi_stop(&rkisp1->csi);
> 		rkisp1_isp_stop(rkisp1);
>@@ -762,35 +761,33 @@ static int rkisp1_isp_s_stream(struct v4l2_subdev *sd, int enable)
> 		return 0;
> 	}
>
>-	sensor_sd = rkisp1_get_remote_sensor(sd);
>-	if (!sensor_sd) {
>-		dev_warn(rkisp1->dev, "No link between isp and sensor\n");
>+	rkisp1->source = rkisp1_get_remote_source(sd);
>+	if (!rkisp1->source) {
>+		dev_warn(rkisp1->dev, "No link between isp and source\n");
> 		return -ENODEV;
> 	}
>
>-	rkisp1->active_sensor = container_of(sensor_sd->asd,
>-					     struct rkisp1_sensor_async, asd);
>+	asd = container_of(rkisp1->source->asd, struct rkisp1_sensor_async,
>+			   asd);
>
>-	if (rkisp1->active_sensor->mbus_type != V4L2_MBUS_CSI2_DPHY)
>+	if (asd->mbus_type != V4L2_MBUS_CSI2_DPHY)
> 		return -EINVAL;
>
> 	rkisp1->isp.frame_sequence = -1;
> 	mutex_lock(&isp->ops_lock);
>-	ret = rkisp1_config_cif(rkisp1, rkisp1->active_sensor->mbus_type,
>-				rkisp1->active_sensor->mbus_flags);
>+	ret = rkisp1_config_cif(rkisp1, asd->mbus_type, asd->mbus_flags);
> 	if (ret)
> 		goto mutex_unlock;
>
> 	rkisp1_isp_start(rkisp1);
>
>-	ret = rkisp1_csi_start(&rkisp1->csi, rkisp1->active_sensor);
>+	ret = rkisp1_csi_start(&rkisp1->csi, asd);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		goto mutex_unlock;
> 	}
>
>-	ret = v4l2_subdev_call(rkisp1->active_sensor->sd, video, s_stream,
>-			       true);
>+	ret = v4l2_subdev_call(rkisp1->source, video, s_stream, true);
> 	if (ret) {
> 		rkisp1_isp_stop(rkisp1);
> 		rkisp1_csi_stop(&rkisp1->csi);
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
  2022-06-25 11:03       ` Laurent Pinchart
@ 2022-07-01  4:48         ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  4:48 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 25.06.2022 14:03, Laurent Pinchart wrote:
>Hi Dafna,
>
>On Sat, Jun 25, 2022 at 10:00:34AM +0300, Dafna Hirschfeld wrote:
>> On 15.06.2022 04:11, Paul Elder wrote:
>> >The CSI receiver is a component separate from the ISP or the resizers.
>> >It is actually optional, not all device model include a CSI receiver. On
>> >some SoCs CSI-2 support can be provided through an external CSI-2
>> >receiver, connected to the ISP's parallel input.
>> >
>> >To support those use cases, create a V4L2 subdev to model the CSI
>> >receiver. It will allow the driver to handle both internal and external
>> >CSI receivers the same way.
>> >
>> >The next commit will plumb the CSI subdev to the rest of the driver,
>> >replacing direct function calls.
>> >
>> >Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>> >Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>> >---
>> > .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
>> > .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
>> > .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
>> > .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
>> > 4 files changed, 313 insertions(+)
>> >
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> >index 3c55e922346e..0ab49d1feb55 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> >@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
>> > 	RKISP1_RSZ_PAD_MAX
>> > };
>> >
>> >+/* enum for the csi receiver pads */
>> >+enum rkisp1_csi_pad {
>> >+	RKISP1_CSI_PAD_SINK,
>> >+	RKISP1_CSI_PAD_SRC,
>> >+	RKISP1_CSI_PAD_MAX
>>
>> I'd call it RKISP1_CSI_PAD_NUM
>
>OK.
>
>> >+};
>> >+
>> > /* enum for the capture id */
>> > enum rkisp1_stream_id {
>> > 	RKISP1_MAINPATH,
>> >@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
>> >  * @rkisp1: pointer to the rkisp1 device
>> >  * @dphy: a pointer to the phy
>> >  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
>> >+ * @sd: v4l2_subdev variable
>> >+ * @pads: media pads
>> >+ * @pad_cfg: configurations for the pads
>> >+ * @ops_lock: a lock for the subdev ops
>> >+ * @source: source in-use, set when starting streaming
>> >  */
>> > struct rkisp1_csi {
>> > 	struct rkisp1_device *rkisp1;
>> > 	struct phy *dphy;
>> > 	bool is_dphy_errctrl_disabled;
>> >+	struct v4l2_subdev sd;
>> >+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
>> >+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
>> >+	struct mutex ops_lock; /* serialize the subdevice ops */
>> >+	struct rkisp1_sensor_async *source;
>> > };
>> >
>> > /*
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>> >index 425a3b014089..8182694a6fe0 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>> >@@ -15,10 +15,34 @@
>> > #include <linux/phy/phy-mipi-dphy.h>
>> >
>> > #include <media/v4l2-ctrls.h>
>> >+#include <media/v4l2-fwnode.h>
>> >
>> > #include "rkisp1-common.h"
>> > #include "rkisp1-csi.h"
>> >
>> >+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
>> >+
>> >+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
>> >+
>> >+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
>> >+{
>> >+	return container_of(sd, struct rkisp1_csi, sd);
>> >+}
>> >+
>> >+static struct v4l2_mbus_framefmt *
>> >+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
>> >+		       struct v4l2_subdev_state *sd_state,
>> >+		       unsigned int pad, u32 which)
>> >+{
>> >+	struct v4l2_subdev_state state = {
>> >+		.pads = csi->pad_cfg
>> >+	};
>>
>> newline here
>
>I'm surprised checkpatch didn't warn. Fixed.

Maybe you need the checkpatch's '--strict' flag to catch it, don't remember

thanks,
Dafna

>
>> >+	if (which == V4L2_SUBDEV_FORMAT_TRY)
>> >+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
>> >+	else
>> >+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
>> >+}
>> >+
>> > static int rkisp1_csi_config(struct rkisp1_csi *csi,
>> > 			     const struct rkisp1_sensor_async *sensor)
>> > {
>> >@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
>> > 	return IRQ_HANDLED;
>> > }
>> >
>> >+/* ----------------------------------------------------------------------------
>> >+ * Subdev pad operations
>> >+ */
>> >+
>> >+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
>> >+				   struct v4l2_subdev_state *sd_state,
>> >+				   struct v4l2_mbus_framefmt *format,
>> >+				   unsigned int which)
>> >+{
>> >+	struct v4l2_mbus_framefmt *sink_fmt;
>> >+
>> >+	/* We don't set the src format directly; take it from the sink format */
>> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>> >+					  which);
>> >+
>> >+	*format = *sink_fmt;
>> >+}
>> >+
>> >+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
>> >+				    struct v4l2_subdev_state *sd_state,
>> >+				    struct v4l2_mbus_framefmt *format,
>> >+				    unsigned int which)
>> >+{
>> >+	const struct rkisp1_mbus_info *mbus_info;
>> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>> >+
>> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>> >+					  which);
>> >+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
>> >+					 which);
>> >+
>> >+	sink_fmt->code = format->code;
>> >+
>> >+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>> >+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
>> >+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
>> >+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>> >+	}
>> >+
>> >+	sink_fmt->width = clamp_t(u32, format->width,
>> >+				  RKISP1_ISP_MIN_WIDTH,
>> >+				  RKISP1_ISP_MAX_WIDTH);
>> >+	sink_fmt->height = clamp_t(u32, format->height,
>> >+				   RKISP1_ISP_MIN_HEIGHT,
>> >+				   RKISP1_ISP_MAX_HEIGHT);
>> >+
>> >+	/* Propagate to source pad */
>> >+	src_fmt->code = sink_fmt->code;
>> >+	src_fmt->width = sink_fmt->width;
>> >+	src_fmt->height = sink_fmt->height;
>> >+
>>
>> why here you don't do '*src_fmt = *sink_fmt' instead of per field propaget ?
>
>You're right, the CSI-2 receiver doesn't change the format in any way,
>that would be easier.
>
>> >+	*format = *sink_fmt;
>> >+}
>> >+
>> >+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
>> >+				     struct v4l2_subdev_state *sd_state,
>> >+				     struct v4l2_subdev_mbus_code_enum *code)
>> >+{
>> >+	unsigned int i;
>> >+	int pos = 0;
>> >+
>> >+	if (code->index >= rkisp1_mbus_info_length())
>> >+		return -EINVAL;
>> >+
>> >+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
>> >+		const struct rkisp1_mbus_info *fmt =
>> >+			rkisp1_mbus_info_get_by_index(i);
>> >+
>> >+		if (fmt->direction & RKISP1_ISP_SD_SINK)
>> >+			pos++;
>> >+
>> >+		if (code->index == pos - 1) {
>> >+			code->code = fmt->mbus_code;
>> >+			return 0;
>> >+		}
>> >+	}
>> >+
>> >+	return -EINVAL;
>> >+}
>> >+
>> >+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
>> >+				  struct v4l2_subdev_state *sd_state)
>> >+{
>> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>> >+
>> >+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>> >+					      RKISP1_CSI_PAD_SRC);
>>
>> last argument here should be RKISP1_CSI_PAD_SINK ?
>>
>> >+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
>> >+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
>> >+	sink_fmt->field = V4L2_FIELD_NONE;
>> >+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
>> >+
>> >+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>> >+					     RKISP1_CSI_PAD_SINK);
>>
>> last argument here should be RKISP1_CSI_PAD_SRC ?
>
>Yes, the two are swapped, I'll fix that.
>
>> >+	*src_fmt = *sink_fmt;
>> >+
>> >+	return 0;
>> >+}
>> >+
>> >+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
>> >+			      struct v4l2_subdev_state *sd_state,
>> >+			      struct v4l2_subdev_format *fmt)
>> >+{
>> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>> >+
>> >+	mutex_lock(&csi->ops_lock);
>> >+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
>> >+					      fmt->which);
>> >+	mutex_unlock(&csi->ops_lock);
>> >+	return 0;
>> >+}
>> >+
>> >+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
>> >+			      struct v4l2_subdev_state *sd_state,
>> >+			      struct v4l2_subdev_format *fmt)
>> >+{
>> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>> >+
>> >+	mutex_lock(&csi->ops_lock);
>> >+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
>> >+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
>> >+					fmt->which);
>> >+	else
>> >+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
>> >+				       fmt->which);
>> >+
>> >+	mutex_unlock(&csi->ops_lock);
>> >+	return 0;
>> >+}
>> >+
>> >+/* ----------------------------------------------------------------------------
>> >+ * Subdev video operations
>> >+ */
>> >+
>> >+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
>> >+{
>> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>> >+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>> >+	struct media_pad *source_pad;
>> >+	struct v4l2_subdev *source;
>> >+	int ret;
>> >+
>> >+	if (!enable) {
>> >+		v4l2_subdev_call(csi->source->sd, video, s_stream,
>> >+				 false);
>> >+
>> >+		rkisp1_csi_stop(csi);
>> >+
>> >+		return ret;
>>
>> ret is uninitialized here
>
>Fixed.
>
>> >+	}
>> >+
>> >+	source_pad = media_entity_remote_source_pad(&sd->entity);
>> >+	if (IS_ERR(source_pad)) {
>> >+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);
>>
>> here you should print 'ERR_PTR(source_pad)' instead of 'ret'
>
>Indeed.
>
>Thanks for catching all those mistakes.
>
>> >+		return -EPIPE;
>> >+	}
>> >+
>> >+	source = media_entity_to_v4l2_subdev(source_pad->entity);
>> >+	if (!source) {
>> >+		/* This should really not happen, so is not worth a message. */
>> >+		return -EPIPE;
>> >+	}
>> >+
>> >+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
>> >+				   asd);
>> >+
>> >+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
>> >+		return -EINVAL;
>> >+
>> >+	mutex_lock(&csi->ops_lock);
>> >+	ret = rkisp1_csi_start(csi, csi->source);
>> >+	mutex_unlock(&csi->ops_lock);
>> >+	if (ret)
>> >+		return ret;
>> >+
>> >+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
>> >+
>> >+	return 0;
>> >+}
>> >+
>> >+/* ----------------------------------------------------------------------------
>> >+ * Registration
>> >+ */
>> >+
>> >+static const struct media_entity_operations rkisp1_csi_media_ops = {
>> >+	.link_validate = v4l2_subdev_link_validate,
>> >+};
>> >+
>> >+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
>> >+	.s_stream = rkisp1_csi_s_stream,
>> >+};
>> >+
>> >+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
>> >+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
>> >+	.init_cfg = rkisp1_csi_init_config,
>> >+	.get_fmt = rkisp1_csi_get_fmt,
>> >+	.set_fmt = rkisp1_csi_set_fmt,
>> >+};
>> >+
>> >+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
>> >+	.video = &rkisp1_csi_video_ops,
>> >+	.pad = &rkisp1_csi_pad_ops,
>> >+};
>> >+
>> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
>> >+{
>> >+	struct rkisp1_csi *csi = &rkisp1->csi;
>> >+	struct v4l2_subdev_state state = {};
>> >+	struct media_pad *pads;
>> >+	struct v4l2_subdev *sd;
>> >+	int ret;
>> >+
>> >+	csi->rkisp1 = rkisp1;
>> >+	mutex_init(&csi->ops_lock);
>> >+
>> >+	sd = &csi->sd;
>> >+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
>> >+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
>> >+	sd->entity.ops = &rkisp1_csi_media_ops;
>> >+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
>> >+	sd->owner = THIS_MODULE;
>> >+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
>> >+
>> >+	pads = csi->pads;
>> >+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
>> >+					  MEDIA_PAD_FL_MUST_CONNECT;
>> >+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
>> >+					 MEDIA_PAD_FL_MUST_CONNECT;
>> >+
>> >+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
>> >+	if (ret)
>> >+		goto error;
>> >+
>> >+	state.pads = csi->pad_cfg;
>> >+	rkisp1_csi_init_config(sd, &state);
>> >+
>> >+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
>> >+	if (ret) {
>> >+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
>> >+		goto error;
>> >+	}
>> >+
>> >+	return 0;
>> >+
>> >+error:
>> >+	media_entity_cleanup(&sd->entity);
>> >+	mutex_destroy(&csi->ops_lock);
>> >+	csi->rkisp1 = NULL;
>> >+	return ret;
>> >+}
>> >+
>> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
>> >+{
>> >+	struct rkisp1_csi *csi = &rkisp1->csi;
>> >+
>> >+	if (!csi->rkisp1)
>> >+		return;
>> >+
>> >+	v4l2_device_unregister_subdev(&csi->sd);
>> >+	media_entity_cleanup(&csi->sd.entity);
>> >+	mutex_destroy(&csi->ops_lock);
>> >+}
>> >+
>> > int rkisp1_csi_init(struct rkisp1_device *rkisp1)
>> > {
>> > 	struct rkisp1_csi *csi = &rkisp1->csi;
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>> >index 97ce7e7959ab..ddf8e5e08f55 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>> >@@ -13,10 +13,14 @@
>> >
>> > struct rkisp1_device;
>> > struct rkisp1_sensor_async;
>> >+struct v4l2_subdev;
>> >
>> > int rkisp1_csi_init(struct rkisp1_device *rkisp1);
>> > void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>> >
>> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
>> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>> >+
>> > int rkisp1_csi_start(struct rkisp1_csi *csi,
>> > 		     const struct rkisp1_sensor_async *sensor);
>> > void rkisp1_csi_stop(struct rkisp1_csi *csi);
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> >index 253220188abd..faf2cd4c8149 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> >@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>> >
>> > static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
>> > {
>> >+	rkisp1_csi_unregister(rkisp1);
>> > 	rkisp1_params_unregister(rkisp1);
>> > 	rkisp1_stats_unregister(rkisp1);
>> > 	rkisp1_capture_devs_unregister(rkisp1);
>> >@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
>> > 	if (ret)
>> > 		goto error;
>> >
>> >+	ret = rkisp1_csi_register(rkisp1);
>> >+	if (ret)
>> >+		goto error;
>> >+
>> > 	ret = rkisp1_create_links(rkisp1);
>> > 	if (ret)
>> > 		goto error;
>
>-- 
>Regards,
>
>Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver
@ 2022-07-01  4:48         ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  4:48 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 25.06.2022 14:03, Laurent Pinchart wrote:
>Hi Dafna,
>
>On Sat, Jun 25, 2022 at 10:00:34AM +0300, Dafna Hirschfeld wrote:
>> On 15.06.2022 04:11, Paul Elder wrote:
>> >The CSI receiver is a component separate from the ISP or the resizers.
>> >It is actually optional, not all device model include a CSI receiver. On
>> >some SoCs CSI-2 support can be provided through an external CSI-2
>> >receiver, connected to the ISP's parallel input.
>> >
>> >To support those use cases, create a V4L2 subdev to model the CSI
>> >receiver. It will allow the driver to handle both internal and external
>> >CSI receivers the same way.
>> >
>> >The next commit will plumb the CSI subdev to the rest of the driver,
>> >replacing direct function calls.
>> >
>> >Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>> >Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>> >---
>> > .../platform/rockchip/rkisp1/rkisp1-common.h  |  17 ++
>> > .../platform/rockchip/rkisp1/rkisp1-csi.c     | 287 ++++++++++++++++++
>> > .../platform/rockchip/rkisp1/rkisp1-csi.h     |   4 +
>> > .../platform/rockchip/rkisp1/rkisp1-dev.c     |   5 +
>> > 4 files changed, 313 insertions(+)
>> >
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> >index 3c55e922346e..0ab49d1feb55 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> >@@ -68,6 +68,13 @@ enum rkisp1_rsz_pad {
>> > 	RKISP1_RSZ_PAD_MAX
>> > };
>> >
>> >+/* enum for the csi receiver pads */
>> >+enum rkisp1_csi_pad {
>> >+	RKISP1_CSI_PAD_SINK,
>> >+	RKISP1_CSI_PAD_SRC,
>> >+	RKISP1_CSI_PAD_MAX
>>
>> I'd call it RKISP1_CSI_PAD_NUM
>
>OK.
>
>> >+};
>> >+
>> > /* enum for the capture id */
>> > enum rkisp1_stream_id {
>> > 	RKISP1_MAINPATH,
>> >@@ -141,11 +148,21 @@ struct rkisp1_sensor_async {
>> >  * @rkisp1: pointer to the rkisp1 device
>> >  * @dphy: a pointer to the phy
>> >  * @is_dphy_errctrl_disabled: if dphy errctrl is disabled (avoid endless interrupt)
>> >+ * @sd: v4l2_subdev variable
>> >+ * @pads: media pads
>> >+ * @pad_cfg: configurations for the pads
>> >+ * @ops_lock: a lock for the subdev ops
>> >+ * @source: source in-use, set when starting streaming
>> >  */
>> > struct rkisp1_csi {
>> > 	struct rkisp1_device *rkisp1;
>> > 	struct phy *dphy;
>> > 	bool is_dphy_errctrl_disabled;
>> >+	struct v4l2_subdev sd;
>> >+	struct media_pad pads[RKISP1_CSI_PAD_MAX];
>> >+	struct v4l2_subdev_pad_config pad_cfg[RKISP1_CSI_PAD_MAX];
>> >+	struct mutex ops_lock; /* serialize the subdevice ops */
>> >+	struct rkisp1_sensor_async *source;
>> > };
>> >
>> > /*
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>> >index 425a3b014089..8182694a6fe0 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.c
>> >@@ -15,10 +15,34 @@
>> > #include <linux/phy/phy-mipi-dphy.h>
>> >
>> > #include <media/v4l2-ctrls.h>
>> >+#include <media/v4l2-fwnode.h>
>> >
>> > #include "rkisp1-common.h"
>> > #include "rkisp1-csi.h"
>> >
>> >+#define RKISP1_CSI_DEV_NAME	RKISP1_DRIVER_NAME "_csi"
>> >+
>> >+#define RKISP1_CSI_DEF_FMT	MEDIA_BUS_FMT_SRGGB10_1X10
>> >+
>> >+static inline struct rkisp1_csi *to_rkisp1_csi(struct v4l2_subdev *sd)
>> >+{
>> >+	return container_of(sd, struct rkisp1_csi, sd);
>> >+}
>> >+
>> >+static struct v4l2_mbus_framefmt *
>> >+rkisp1_csi_get_pad_fmt(struct rkisp1_csi *csi,
>> >+		       struct v4l2_subdev_state *sd_state,
>> >+		       unsigned int pad, u32 which)
>> >+{
>> >+	struct v4l2_subdev_state state = {
>> >+		.pads = csi->pad_cfg
>> >+	};
>>
>> newline here
>
>I'm surprised checkpatch didn't warn. Fixed.

Maybe you need the checkpatch's '--strict' flag to catch it, don't remember

thanks,
Dafna

>
>> >+	if (which == V4L2_SUBDEV_FORMAT_TRY)
>> >+		return v4l2_subdev_get_try_format(&csi->sd, sd_state, pad);
>> >+	else
>> >+		return v4l2_subdev_get_try_format(&csi->sd, &state, pad);
>> >+}
>> >+
>> > static int rkisp1_csi_config(struct rkisp1_csi *csi,
>> > 			     const struct rkisp1_sensor_async *sensor)
>> > {
>> >@@ -185,6 +209,269 @@ irqreturn_t rkisp1_csi_isr(int irq, void *ctx)
>> > 	return IRQ_HANDLED;
>> > }
>> >
>> >+/* ----------------------------------------------------------------------------
>> >+ * Subdev pad operations
>> >+ */
>> >+
>> >+static void rkisp1_csi_set_src_fmt(struct rkisp1_csi *csi,
>> >+				   struct v4l2_subdev_state *sd_state,
>> >+				   struct v4l2_mbus_framefmt *format,
>> >+				   unsigned int which)
>> >+{
>> >+	struct v4l2_mbus_framefmt *sink_fmt;
>> >+
>> >+	/* We don't set the src format directly; take it from the sink format */
>> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>> >+					  which);
>> >+
>> >+	*format = *sink_fmt;
>> >+}
>> >+
>> >+static void rkisp1_csi_set_sink_fmt(struct rkisp1_csi *csi,
>> >+				    struct v4l2_subdev_state *sd_state,
>> >+				    struct v4l2_mbus_framefmt *format,
>> >+				    unsigned int which)
>> >+{
>> >+	const struct rkisp1_mbus_info *mbus_info;
>> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>> >+
>> >+	sink_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SINK,
>> >+					  which);
>> >+	src_fmt = rkisp1_csi_get_pad_fmt(csi, sd_state, RKISP1_CSI_PAD_SRC,
>> >+					 which);
>> >+
>> >+	sink_fmt->code = format->code;
>> >+
>> >+	mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>> >+	if (!mbus_info || !(mbus_info->direction & RKISP1_ISP_SD_SINK)) {
>> >+		sink_fmt->code = RKISP1_CSI_DEF_FMT;
>> >+		mbus_info = rkisp1_mbus_info_get_by_code(sink_fmt->code);
>> >+	}
>> >+
>> >+	sink_fmt->width = clamp_t(u32, format->width,
>> >+				  RKISP1_ISP_MIN_WIDTH,
>> >+				  RKISP1_ISP_MAX_WIDTH);
>> >+	sink_fmt->height = clamp_t(u32, format->height,
>> >+				   RKISP1_ISP_MIN_HEIGHT,
>> >+				   RKISP1_ISP_MAX_HEIGHT);
>> >+
>> >+	/* Propagate to source pad */
>> >+	src_fmt->code = sink_fmt->code;
>> >+	src_fmt->width = sink_fmt->width;
>> >+	src_fmt->height = sink_fmt->height;
>> >+
>>
>> why here you don't do '*src_fmt = *sink_fmt' instead of per field propaget ?
>
>You're right, the CSI-2 receiver doesn't change the format in any way,
>that would be easier.
>
>> >+	*format = *sink_fmt;
>> >+}
>> >+
>> >+static int rkisp1_csi_enum_mbus_code(struct v4l2_subdev *sd,
>> >+				     struct v4l2_subdev_state *sd_state,
>> >+				     struct v4l2_subdev_mbus_code_enum *code)
>> >+{
>> >+	unsigned int i;
>> >+	int pos = 0;
>> >+
>> >+	if (code->index >= rkisp1_mbus_info_length())
>> >+		return -EINVAL;
>> >+
>> >+	for (i = 0; i < rkisp1_mbus_info_length(); i++) {
>> >+		const struct rkisp1_mbus_info *fmt =
>> >+			rkisp1_mbus_info_get_by_index(i);
>> >+
>> >+		if (fmt->direction & RKISP1_ISP_SD_SINK)
>> >+			pos++;
>> >+
>> >+		if (code->index == pos - 1) {
>> >+			code->code = fmt->mbus_code;
>> >+			return 0;
>> >+		}
>> >+	}
>> >+
>> >+	return -EINVAL;
>> >+}
>> >+
>> >+static int rkisp1_csi_init_config(struct v4l2_subdev *sd,
>> >+				  struct v4l2_subdev_state *sd_state)
>> >+{
>> >+	struct v4l2_mbus_framefmt *sink_fmt, *src_fmt;
>> >+
>> >+	sink_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>> >+					      RKISP1_CSI_PAD_SRC);
>>
>> last argument here should be RKISP1_CSI_PAD_SINK ?
>>
>> >+	sink_fmt->width = RKISP1_DEFAULT_WIDTH;
>> >+	sink_fmt->height = RKISP1_DEFAULT_HEIGHT;
>> >+	sink_fmt->field = V4L2_FIELD_NONE;
>> >+	sink_fmt->code = RKISP1_CSI_DEF_FMT;
>> >+
>> >+	src_fmt = v4l2_subdev_get_try_format(sd, sd_state,
>> >+					     RKISP1_CSI_PAD_SINK);
>>
>> last argument here should be RKISP1_CSI_PAD_SRC ?
>
>Yes, the two are swapped, I'll fix that.
>
>> >+	*src_fmt = *sink_fmt;
>> >+
>> >+	return 0;
>> >+}
>> >+
>> >+static int rkisp1_csi_get_fmt(struct v4l2_subdev *sd,
>> >+			      struct v4l2_subdev_state *sd_state,
>> >+			      struct v4l2_subdev_format *fmt)
>> >+{
>> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>> >+
>> >+	mutex_lock(&csi->ops_lock);
>> >+	fmt->format = *rkisp1_csi_get_pad_fmt(csi, sd_state, fmt->pad,
>> >+					      fmt->which);
>> >+	mutex_unlock(&csi->ops_lock);
>> >+	return 0;
>> >+}
>> >+
>> >+static int rkisp1_csi_set_fmt(struct v4l2_subdev *sd,
>> >+			      struct v4l2_subdev_state *sd_state,
>> >+			      struct v4l2_subdev_format *fmt)
>> >+{
>> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>> >+
>> >+	mutex_lock(&csi->ops_lock);
>> >+	if (fmt->pad == RKISP1_CSI_PAD_SINK)
>> >+		rkisp1_csi_set_sink_fmt(csi, sd_state, &fmt->format,
>> >+					fmt->which);
>> >+	else
>> >+		rkisp1_csi_set_src_fmt(csi, sd_state, &fmt->format,
>> >+				       fmt->which);
>> >+
>> >+	mutex_unlock(&csi->ops_lock);
>> >+	return 0;
>> >+}
>> >+
>> >+/* ----------------------------------------------------------------------------
>> >+ * Subdev video operations
>> >+ */
>> >+
>> >+static int rkisp1_csi_s_stream(struct v4l2_subdev *sd, int enable)
>> >+{
>> >+	struct rkisp1_csi *csi = to_rkisp1_csi(sd);
>> >+	struct rkisp1_device *rkisp1 = csi->rkisp1;
>> >+	struct media_pad *source_pad;
>> >+	struct v4l2_subdev *source;
>> >+	int ret;
>> >+
>> >+	if (!enable) {
>> >+		v4l2_subdev_call(csi->source->sd, video, s_stream,
>> >+				 false);
>> >+
>> >+		rkisp1_csi_stop(csi);
>> >+
>> >+		return ret;
>>
>> ret is uninitialized here
>
>Fixed.
>
>> >+	}
>> >+
>> >+	source_pad = media_entity_remote_source_pad(&sd->entity);
>> >+	if (IS_ERR(source_pad)) {
>> >+		dev_dbg(rkisp1->dev, "Failed to get source for CSI: %d\n", ret);
>>
>> here you should print 'ERR_PTR(source_pad)' instead of 'ret'
>
>Indeed.
>
>Thanks for catching all those mistakes.
>
>> >+		return -EPIPE;
>> >+	}
>> >+
>> >+	source = media_entity_to_v4l2_subdev(source_pad->entity);
>> >+	if (!source) {
>> >+		/* This should really not happen, so is not worth a message. */
>> >+		return -EPIPE;
>> >+	}
>> >+
>> >+	csi->source = container_of(source->asd, struct rkisp1_sensor_async,
>> >+				   asd);
>> >+
>> >+	if (csi->source->mbus_type != V4L2_MBUS_CSI2_DPHY)
>> >+		return -EINVAL;
>> >+
>> >+	mutex_lock(&csi->ops_lock);
>> >+	ret = rkisp1_csi_start(csi, csi->source);
>> >+	mutex_unlock(&csi->ops_lock);
>> >+	if (ret)
>> >+		return ret;
>> >+
>> >+	v4l2_subdev_call(csi->source->sd, video, s_stream, true);
>> >+
>> >+	return 0;
>> >+}
>> >+
>> >+/* ----------------------------------------------------------------------------
>> >+ * Registration
>> >+ */
>> >+
>> >+static const struct media_entity_operations rkisp1_csi_media_ops = {
>> >+	.link_validate = v4l2_subdev_link_validate,
>> >+};
>> >+
>> >+static const struct v4l2_subdev_video_ops rkisp1_csi_video_ops = {
>> >+	.s_stream = rkisp1_csi_s_stream,
>> >+};
>> >+
>> >+static const struct v4l2_subdev_pad_ops rkisp1_csi_pad_ops = {
>> >+	.enum_mbus_code = rkisp1_csi_enum_mbus_code,
>> >+	.init_cfg = rkisp1_csi_init_config,
>> >+	.get_fmt = rkisp1_csi_get_fmt,
>> >+	.set_fmt = rkisp1_csi_set_fmt,
>> >+};
>> >+
>> >+static const struct v4l2_subdev_ops rkisp1_csi_ops = {
>> >+	.video = &rkisp1_csi_video_ops,
>> >+	.pad = &rkisp1_csi_pad_ops,
>> >+};
>> >+
>> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1)
>> >+{
>> >+	struct rkisp1_csi *csi = &rkisp1->csi;
>> >+	struct v4l2_subdev_state state = {};
>> >+	struct media_pad *pads;
>> >+	struct v4l2_subdev *sd;
>> >+	int ret;
>> >+
>> >+	csi->rkisp1 = rkisp1;
>> >+	mutex_init(&csi->ops_lock);
>> >+
>> >+	sd = &csi->sd;
>> >+	v4l2_subdev_init(sd, &rkisp1_csi_ops);
>> >+	sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
>> >+	sd->entity.ops = &rkisp1_csi_media_ops;
>> >+	sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
>> >+	sd->owner = THIS_MODULE;
>> >+	strscpy(sd->name, RKISP1_CSI_DEV_NAME, sizeof(sd->name));
>> >+
>> >+	pads = csi->pads;
>> >+	pads[RKISP1_CSI_PAD_SINK].flags = MEDIA_PAD_FL_SINK |
>> >+					  MEDIA_PAD_FL_MUST_CONNECT;
>> >+	pads[RKISP1_CSI_PAD_SRC].flags = MEDIA_PAD_FL_SOURCE |
>> >+					 MEDIA_PAD_FL_MUST_CONNECT;
>> >+
>> >+	ret = media_entity_pads_init(&sd->entity, RKISP1_CSI_PAD_MAX, pads);
>> >+	if (ret)
>> >+		goto error;
>> >+
>> >+	state.pads = csi->pad_cfg;
>> >+	rkisp1_csi_init_config(sd, &state);
>> >+
>> >+	ret = v4l2_device_register_subdev(&csi->rkisp1->v4l2_dev, sd);
>> >+	if (ret) {
>> >+		dev_err(sd->dev, "Failed to register csi receiver subdev\n");
>> >+		goto error;
>> >+	}
>> >+
>> >+	return 0;
>> >+
>> >+error:
>> >+	media_entity_cleanup(&sd->entity);
>> >+	mutex_destroy(&csi->ops_lock);
>> >+	csi->rkisp1 = NULL;
>> >+	return ret;
>> >+}
>> >+
>> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1)
>> >+{
>> >+	struct rkisp1_csi *csi = &rkisp1->csi;
>> >+
>> >+	if (!csi->rkisp1)
>> >+		return;
>> >+
>> >+	v4l2_device_unregister_subdev(&csi->sd);
>> >+	media_entity_cleanup(&csi->sd.entity);
>> >+	mutex_destroy(&csi->ops_lock);
>> >+}
>> >+
>> > int rkisp1_csi_init(struct rkisp1_device *rkisp1)
>> > {
>> > 	struct rkisp1_csi *csi = &rkisp1->csi;
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>> >index 97ce7e7959ab..ddf8e5e08f55 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-csi.h
>> >@@ -13,10 +13,14 @@
>> >
>> > struct rkisp1_device;
>> > struct rkisp1_sensor_async;
>> >+struct v4l2_subdev;
>> >
>> > int rkisp1_csi_init(struct rkisp1_device *rkisp1);
>> > void rkisp1_csi_cleanup(struct rkisp1_device *rkisp1);
>> >
>> >+int rkisp1_csi_register(struct rkisp1_device *rkisp1);
>> >+void rkisp1_csi_unregister(struct rkisp1_device *rkisp1);
>> >+
>> > int rkisp1_csi_start(struct rkisp1_csi *csi,
>> > 		     const struct rkisp1_sensor_async *sensor);
>> > void rkisp1_csi_stop(struct rkisp1_csi *csi);
>> >diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> >index 253220188abd..faf2cd4c8149 100644
>> >--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> >+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> >@@ -324,6 +324,7 @@ static int rkisp1_create_links(struct rkisp1_device *rkisp1)
>> >
>> > static void rkisp1_entities_unregister(struct rkisp1_device *rkisp1)
>> > {
>> >+	rkisp1_csi_unregister(rkisp1);
>> > 	rkisp1_params_unregister(rkisp1);
>> > 	rkisp1_stats_unregister(rkisp1);
>> > 	rkisp1_capture_devs_unregister(rkisp1);
>> >@@ -355,6 +356,10 @@ static int rkisp1_entities_register(struct rkisp1_device *rkisp1)
>> > 	if (ret)
>> > 		goto error;
>> >
>> >+	ret = rkisp1_csi_register(rkisp1);
>> >+	if (ret)
>> >+		goto error;
>> >+
>> > 	ret = rkisp1_create_links(rkisp1);
>> > 	if (ret)
>> > 		goto error;
>
>-- 
>Regards,
>
>Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
  2022-06-14 19:11   ` Paul Elder
@ 2022-07-01  5:22     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:22 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The rkisp1 can take an input on the parallel interface. Add a port for
>it, and update the required field. At least one port is required, and
>both may be specified.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
> 1 file changed, 21 insertions(+), 2 deletions(-)
>
>diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
>index d1489b177331..b3661d7d4357 100644
>--- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
>+++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
>@@ -84,8 +84,27 @@ properties:
>                 minItems: 1
>                 maxItems: 4
>
>-    required:
>-      - port@0
>+      port@1:
>+        $ref: /schemas/graph.yaml#/$defs/port-base
>+        unevaluatedProperties: false
>+        description: connection point for input on the parallel interface
>+
>+        properties:
>+          bus-type:
>+            enum: [5, 6]
>+
>+          endpoint:
>+            $ref: video-interfaces.yaml#
>+            unevaluatedProperties: false
>+
>+        required:
>+          - bus-type
>+
>+    anyOf:
>+      - required:
>+          - port@0
>+      - required:
>+          - port@1
>
> required:
>   - compatible

Could be nice to add an example

thanks,
Dafna

>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
@ 2022-07-01  5:22     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:22 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The rkisp1 can take an input on the parallel interface. Add a port for
>it, and update the required field. At least one port is required, and
>both may be specified.
>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
> 1 file changed, 21 insertions(+), 2 deletions(-)
>
>diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
>index d1489b177331..b3661d7d4357 100644
>--- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
>+++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
>@@ -84,8 +84,27 @@ properties:
>                 minItems: 1
>                 maxItems: 4
>
>-    required:
>-      - port@0
>+      port@1:
>+        $ref: /schemas/graph.yaml#/$defs/port-base
>+        unevaluatedProperties: false
>+        description: connection point for input on the parallel interface
>+
>+        properties:
>+          bus-type:
>+            enum: [5, 6]
>+
>+          endpoint:
>+            $ref: video-interfaces.yaml#
>+            unevaluatedProperties: false
>+
>+        required:
>+          - bus-type
>+
>+    anyOf:
>+      - required:
>+          - port@0
>+      - required:
>+          - port@1
>
> required:
>   - compatible

Could be nice to add an example

thanks,
Dafna

>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
  2022-06-14 19:11   ` Paul Elder
@ 2022-07-01  5:37     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:37 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The ISP version in the i.MX8MP has a separate set of registers for crop
>that is currently not handled. Add a feature flag to determine which
>type of crop the ISP supports and set the crop registers based on that.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
> .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
> .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
> 5 files changed, 46 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 667fca0fef95..e4f422bed09a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
>  */
> enum rkisp1_feature {
> 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
>+	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>+	RKISP1_FEATURE_RSZ_CROP = BIT(2),

Missing documentation for these new features

thanks,
Dafna

> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
>index 02854e8ea1a4..753abd024ce7 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
>@@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> 		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
> 		{ /* Sentinel */ },
> 	};
>+	static const struct rkisp1_debug_register crop_registers[] = {
>+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
>+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
>+		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
>+		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
>+		{ /* Sentinel */ },
>+	};
> 	struct rkisp1_resizer *rsz = m->private;
>
>-	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
>+	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
>+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
>+		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
>+				       crop_registers);
>+
>+	return 0;
> }
> DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index a4496ee2e9b4..5abe33f5fed4 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
> 	.isrs = px30_isp_isrs,
> 	.isr_size = ARRAY_SIZE(px30_isp_isrs),
> 	.isp_ver = RKISP1_V12,
>-	.features = RKISP1_FEATURE_MIPI_CSI2,
>+	.features = RKISP1_FEATURE_MIPI_CSI2
>+		  | RKISP1_FEATURE_DUAL_CROP,
> };
>
> static const char * const rk3399_isp_clks[] = {
>@@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
> 	.isrs = rk3399_isp_isrs,
> 	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
> 	.isp_ver = RKISP1_V10,
>-	.features = RKISP1_FEATURE_MIPI_CSI2,
>+	.features = RKISP1_FEATURE_MIPI_CSI2
>+		  | RKISP1_FEATURE_DUAL_CROP,
> };
>
> static const char * const imx8mp_isp_clks[] = {
>@@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
> 	.isrs = imx8mp_isp_isrs,
> 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> 	.isp_ver = IMX8MP_V10,
>+	.features = RKISP1_FEATURE_RSZ_CROP,
> };
>
> static const struct of_device_id rkisp1_of_match[] = {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>index dd3e6c38be67..1fc54ab22b6d 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>@@ -168,6 +168,9 @@
> #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
>
>+/* RSZ_CROP_[XY]_DIR */
>+#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
>+
> /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
> #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
> #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
>@@ -926,6 +929,12 @@
> #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
> #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
> #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
>+#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
>+#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
>+#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
>+#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
>+#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
>
> #define RKISP1_CIF_MI_BASE			0x00001400
> #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>index f4caa8f684aa..08bf3aa8088f 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>@@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
> {
> 	u32 ratio, rsz_ctrl = 0;
> 	unsigned int i;
>+	u32 val;
>
> 	/* No phase offset */
> 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
>@@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
>
> 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
>
>+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
>+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
>+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
>+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
>+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
>+
>+		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
>+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
>+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;
>+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
>+	}
>+
> 	rkisp1_rsz_update_shadow(rsz, when);
> }
>
>@@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
> 	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
>
> 	if (!enable) {
>-		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
>+		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
>+			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> 		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> 		return 0;
> 	}
>@@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	mutex_lock(&rsz->ops_lock);
> 	rkisp1_rsz_config(rsz, when);
>-	rkisp1_dcrop_config(rsz);
>+	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
>+		rkisp1_dcrop_config(rsz);
>
> 	mutex_unlock(&rsz->ops_lock);
> 	return 0;
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
@ 2022-07-01  5:37     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:37 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The ISP version in the i.MX8MP has a separate set of registers for crop
>that is currently not handled. Add a feature flag to determine which
>type of crop the ISP supports and set the crop registers based on that.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
> .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
> .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
> .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
> 5 files changed, 46 insertions(+), 5 deletions(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index 667fca0fef95..e4f422bed09a 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
>  */
> enum rkisp1_feature {
> 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
>+	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>+	RKISP1_FEATURE_RSZ_CROP = BIT(2),

Missing documentation for these new features

thanks,
Dafna

> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
>index 02854e8ea1a4..753abd024ce7 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
>@@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> 		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
> 		{ /* Sentinel */ },
> 	};
>+	static const struct rkisp1_debug_register crop_registers[] = {
>+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
>+		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
>+		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
>+		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
>+		{ /* Sentinel */ },
>+	};
> 	struct rkisp1_resizer *rsz = m->private;
>
>-	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
>+	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
>+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
>+		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
>+				       crop_registers);
>+
>+	return 0;
> }
> DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index a4496ee2e9b4..5abe33f5fed4 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
> 	.isrs = px30_isp_isrs,
> 	.isr_size = ARRAY_SIZE(px30_isp_isrs),
> 	.isp_ver = RKISP1_V12,
>-	.features = RKISP1_FEATURE_MIPI_CSI2,
>+	.features = RKISP1_FEATURE_MIPI_CSI2
>+		  | RKISP1_FEATURE_DUAL_CROP,
> };
>
> static const char * const rk3399_isp_clks[] = {
>@@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
> 	.isrs = rk3399_isp_isrs,
> 	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
> 	.isp_ver = RKISP1_V10,
>-	.features = RKISP1_FEATURE_MIPI_CSI2,
>+	.features = RKISP1_FEATURE_MIPI_CSI2
>+		  | RKISP1_FEATURE_DUAL_CROP,
> };
>
> static const char * const imx8mp_isp_clks[] = {
>@@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
> 	.isrs = imx8mp_isp_isrs,
> 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> 	.isp_ver = IMX8MP_V10,
>+	.features = RKISP1_FEATURE_RSZ_CROP,
> };
>
> static const struct of_device_id rkisp1_of_match[] = {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>index dd3e6c38be67..1fc54ab22b6d 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>@@ -168,6 +168,9 @@
> #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
>
>+/* RSZ_CROP_[XY]_DIR */
>+#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
>+
> /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
> #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
> #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
>@@ -926,6 +929,12 @@
> #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
> #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
> #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
>+#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
>+#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
>+#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
>+#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
>+#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
>
> #define RKISP1_CIF_MI_BASE			0x00001400
> #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>index f4caa8f684aa..08bf3aa8088f 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
>@@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
> {
> 	u32 ratio, rsz_ctrl = 0;
> 	unsigned int i;
>+	u32 val;
>
> 	/* No phase offset */
> 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
>@@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
>
> 	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
>
>+	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
>+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
>+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
>+		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
>+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
>+
>+		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
>+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
>+		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;
>+		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
>+	}
>+
> 	rkisp1_rsz_update_shadow(rsz, when);
> }
>
>@@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
> 	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
>
> 	if (!enable) {
>-		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
>+		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
>+			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> 		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> 		return 0;
> 	}
>@@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
>
> 	mutex_lock(&rsz->ops_lock);
> 	rkisp1_rsz_config(rsz, when);
>-	rkisp1_dcrop_config(rsz);
>+	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
>+		rkisp1_dcrop_config(rsz);
>
> 	mutex_unlock(&rsz->ops_lock);
> 	return 0;
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP
  2022-06-14 19:11   ` Paul Elder
@ 2022-07-01  5:40     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:40 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The ISP version in the i.MX8MP has a set of registers currently not
>handled by the driver for output size configuration. Add a feature flag
>to determine if the ISP requires this, and set the registers based on
>that.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c | 8 ++++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-common.h  | 1 +
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c     | 3 ++-
> drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h    | 9 +++++++++
> 4 files changed, 20 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>index 9edaa95fa44c..35cec263c563 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>@@ -420,6 +420,14 @@ static void rkisp1_mp_config(struct rkisp1_capture *cap)
> 	rkisp1_write(rkisp1, cap->config->mi.cr_size_init,
> 		     rkisp1_pixfmt_comp_size(pixm, RKISP1_PLANE_CR));
>
>+	if (rkisp1->info->features & RKISP1_FEATURE_MAIN_STRIDE) {
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_LLENGTH, pixm->width);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_WIDTH, pixm->width);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_HEIGHT, pixm->height);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_SIZE,
>+			     pixm->width * pixm->height);
>+	}
>+
> 	rkisp1_irq_frame_end_enable(cap);
>
> 	/* set uv swapping for semiplanar formats */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index e4f422bed09a..96657e55a5b0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -112,6 +112,7 @@ enum rkisp1_feature {
> 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
> 	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> 	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>+	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),

Missing doc for this one,

thanks,
Dafna

> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 5abe33f5fed4..d68a805e8b6b 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -505,7 +505,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
> 	.isrs = imx8mp_isp_isrs,
> 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> 	.isp_ver = IMX8MP_V10,
>-	.features = RKISP1_FEATURE_RSZ_CROP,
>+	.features = RKISP1_FEATURE_RSZ_CROP
>+		  | RKISP1_FEATURE_MAIN_STRIDE,
> };
>
> static const struct of_device_id rkisp1_of_match[] = {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>index 1fc54ab22b6d..5c2195019723 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>@@ -1013,6 +1013,15 @@
> #define RKISP1_CIF_MI_SP_CB_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000140)
> #define RKISP1_CIF_MI_SP_CR_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000144)
> #define RKISP1_CIF_MI_XTD_FORMAT_CTRL		(RKISP1_CIF_MI_BASE + 0x00000148)
>+#define RKISP1_CIF_MI_MP_HANDSHAKE_0		(RKISP1_CIF_MI_BASE + 0x0000014C)
>+#define RKISP1_CIF_MI_MP_Y_LLENGTH		(RKISP1_CIF_MI_BASE + 0x00000150)
>+#define RKISP1_CIF_MI_MP_Y_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000154)
>+#define RKISP1_CIF_MI_MP_C_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000158)
>+#define RKISP1_CIF_MI_OUTPUT_ALIGN_FORMAT	(RKISP1_CIF_MI_BASE + 0x0000015C)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE	(RKISP1_CIF_MI_BASE + 0x00000160)
>+#define RKISP1_CIF_MI_MP_Y_PIC_WIDTH		(RKISP1_CIF_MI_BASE + 0x00000164)
>+#define RKISP1_CIF_MI_MP_Y_PIC_HEIGHT		(RKISP1_CIF_MI_BASE + 0x00000168)
>+#define RKISP1_CIF_MI_MP_Y_PIC_SIZE		(RKISP1_CIF_MI_BASE + 0x0000016C)
>
> #define RKISP1_CIF_SMIA_BASE			0x00001A00
> #define RKISP1_CIF_SMIA_CTRL			(RKISP1_CIF_SMIA_BASE + 0x00000000)
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP
@ 2022-07-01  5:40     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:40 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>The ISP version in the i.MX8MP has a set of registers currently not
>handled by the driver for output size configuration. Add a feature flag
>to determine if the ISP requires this, and set the registers based on
>that.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c | 8 ++++++++
> drivers/media/platform/rockchip/rkisp1/rkisp1-common.h  | 1 +
> drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c     | 3 ++-
> drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h    | 9 +++++++++
> 4 files changed, 20 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>index 9edaa95fa44c..35cec263c563 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>@@ -420,6 +420,14 @@ static void rkisp1_mp_config(struct rkisp1_capture *cap)
> 	rkisp1_write(rkisp1, cap->config->mi.cr_size_init,
> 		     rkisp1_pixfmt_comp_size(pixm, RKISP1_PLANE_CR));
>
>+	if (rkisp1->info->features & RKISP1_FEATURE_MAIN_STRIDE) {
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_LLENGTH, pixm->width);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_WIDTH, pixm->width);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_HEIGHT, pixm->height);
>+		rkisp1_write(rkisp1, RKISP1_CIF_MI_MP_Y_PIC_SIZE,
>+			     pixm->width * pixm->height);
>+	}
>+
> 	rkisp1_irq_frame_end_enable(cap);
>
> 	/* set uv swapping for semiplanar formats */
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>index e4f422bed09a..96657e55a5b0 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>@@ -112,6 +112,7 @@ enum rkisp1_feature {
> 	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
> 	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> 	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>+	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),

Missing doc for this one,

thanks,
Dafna

> };
>
> /*
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>index 5abe33f5fed4..d68a805e8b6b 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>@@ -505,7 +505,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
> 	.isrs = imx8mp_isp_isrs,
> 	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> 	.isp_ver = IMX8MP_V10,
>-	.features = RKISP1_FEATURE_RSZ_CROP,
>+	.features = RKISP1_FEATURE_RSZ_CROP
>+		  | RKISP1_FEATURE_MAIN_STRIDE,
> };
>
> static const struct of_device_id rkisp1_of_match[] = {
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>index 1fc54ab22b6d..5c2195019723 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>@@ -1013,6 +1013,15 @@
> #define RKISP1_CIF_MI_SP_CB_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000140)
> #define RKISP1_CIF_MI_SP_CR_BASE_AD_INIT2	(RKISP1_CIF_MI_BASE + 0x00000144)
> #define RKISP1_CIF_MI_XTD_FORMAT_CTRL		(RKISP1_CIF_MI_BASE + 0x00000148)
>+#define RKISP1_CIF_MI_MP_HANDSHAKE_0		(RKISP1_CIF_MI_BASE + 0x0000014C)
>+#define RKISP1_CIF_MI_MP_Y_LLENGTH		(RKISP1_CIF_MI_BASE + 0x00000150)
>+#define RKISP1_CIF_MI_MP_Y_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000154)
>+#define RKISP1_CIF_MI_MP_C_SLICE_OFFSET		(RKISP1_CIF_MI_BASE + 0x00000158)
>+#define RKISP1_CIF_MI_OUTPUT_ALIGN_FORMAT	(RKISP1_CIF_MI_BASE + 0x0000015C)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE	(RKISP1_CIF_MI_BASE + 0x00000160)
>+#define RKISP1_CIF_MI_MP_Y_PIC_WIDTH		(RKISP1_CIF_MI_BASE + 0x00000164)
>+#define RKISP1_CIF_MI_MP_Y_PIC_HEIGHT		(RKISP1_CIF_MI_BASE + 0x00000168)
>+#define RKISP1_CIF_MI_MP_Y_PIC_SIZE		(RKISP1_CIF_MI_BASE + 0x0000016C)
>
> #define RKISP1_CIF_SMIA_BASE			0x00001A00
> #define RKISP1_CIF_SMIA_CTRL			(RKISP1_CIF_SMIA_BASE + 0x00000000)
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 52/55] media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
  2022-06-14 19:11   ` Paul Elder
@ 2022-07-01  5:45     ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:45 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>Add register definitions for resizer format conversion control and for
>the memory interface output that are specific to the ISP version in the
>i.MX8MP.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-regs.h    | 33 +++++++++++++++++++
> 1 file changed, 33 insertions(+)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>index 5c2195019723..dd63ae13e603 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>@@ -171,6 +171,23 @@
> /* RSZ_CROP_[XY]_DIR */
> #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
>
>+/* RSZ_FORMAT_CONV_CTRL */
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_400	(0 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_420	(1 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422	(2 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_444	(3 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_400	(0 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420	(1 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_422	(2 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_444	(3 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_Y_FULL			BIT(5)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_CBCR_FULL			BIT(6)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_422NOCOSITED		BIT(7)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_ENABLE	BIT(8)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_METHOD	BIT(9)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_PLANAR		(0 << 10)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR	(1 << 10)
>+
> /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
> #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
> #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
>@@ -212,6 +229,22 @@
> #define RKISP1_CIF_MI_XTD_FMT_CTRL_MP_CB_CR_SWAP	BIT(0)
> #define RKISP1_CIF_MI_XTD_FMT_CTRL_SP_CB_CR_SWAP	BIT(1)
> #define RKISP1_CIF_MI_XTD_FMT_CTRL_DMA_CB_CR_SWAP	BIT(2)

newline here

>+/* MI_OUTPUT_ALIGN_FORMAT */
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_LSB_ALIGNMENT			BIT(0)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_BYTES		BIT(1)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_WORDS		BIT(2)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_DWORDS		BIT(3)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_BYTES		BIT(4)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_WORDS		BIT(5)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_DWORDS		BIT(6)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_BYTES		BIT(7)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_WORDS		BIT(8)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_DWORDS		BIT(9)

and here,

thanks,
Dafna

>+/* MI_MP_OUTPUT_FIFO_SIZE */
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_FULL	(0 << 0)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_HALF	(1 << 0)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_QUARTER	(2 << 0)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_EIGHT	(3 << 0)
>
> /* VI_CCL */
> #define RKISP1_CIF_CCL_CIF_CLK_DIS			BIT(2)
>-- 
>2.30.2
>

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 52/55] media: rkisp1: Add i.MX8MP-specific registers for MI and resizer
@ 2022-07-01  5:45     ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:45 UTC (permalink / raw)
  To: Paul Elder
  Cc: linux-media, heiko, laurent.pinchart, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

On 15.06.2022 04:11, Paul Elder wrote:
>Add register definitions for resizer format conversion control and for
>the memory interface output that are specific to the ISP version in the
>i.MX8MP.
>
>Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>---
> .../platform/rockchip/rkisp1/rkisp1-regs.h    | 33 +++++++++++++++++++
> 1 file changed, 33 insertions(+)
>
>diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>index 5c2195019723..dd63ae13e603 100644
>--- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>+++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
>@@ -171,6 +171,23 @@
> /* RSZ_CROP_[XY]_DIR */
> #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
>
>+/* RSZ_FORMAT_CONV_CTRL */
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_400	(0 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_420	(1 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422	(2 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_444	(3 << 0)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_400	(0 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420	(1 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_422	(2 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_444	(3 << 2)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_Y_FULL			BIT(5)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_CBCR_FULL			BIT(6)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_CFG_422NOCOSITED		BIT(7)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_ENABLE	BIT(8)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_DATA_WIDTH_10_BIT_METHOD	BIT(9)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_PLANAR		(0 << 10)
>+#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR	(1 << 10)
>+
> /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
> #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
> #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
>@@ -212,6 +229,22 @@
> #define RKISP1_CIF_MI_XTD_FMT_CTRL_MP_CB_CR_SWAP	BIT(0)
> #define RKISP1_CIF_MI_XTD_FMT_CTRL_SP_CB_CR_SWAP	BIT(1)
> #define RKISP1_CIF_MI_XTD_FMT_CTRL_DMA_CB_CR_SWAP	BIT(2)

newline here

>+/* MI_OUTPUT_ALIGN_FORMAT */
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_LSB_ALIGNMENT			BIT(0)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_BYTES		BIT(1)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_WORDS		BIT(2)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_MP_BYTE_SWAP_DWORDS		BIT(3)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_BYTES		BIT(4)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_WORDS		BIT(5)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_SP_BYTE_SWAP_DWORDS		BIT(6)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_BYTES		BIT(7)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_WORDS		BIT(8)
>+#define RKISP1_CIF_OUTPUT_ALIGN_FORMAT_DMA_BYTE_SWAP_DWORDS		BIT(9)

and here,

thanks,
Dafna

>+/* MI_MP_OUTPUT_FIFO_SIZE */
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_FULL	(0 << 0)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_HALF	(1 << 0)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_QUARTER	(2 << 0)
>+#define RKISP1_CIF_MI_MP_OUTPUT_FIFO_SIZE_OUTPUT_FIFO_DEPTH_EIGHT	(3 << 0)
>
> /* VI_CCL */
> #define RKISP1_CIF_CCL_CIF_CLK_DIS			BIT(2)
>-- 
>2.30.2
>

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
  2022-06-26 11:38     ` Laurent Pinchart
@ 2022-07-01  5:53       ` Dafna Hirschfeld
  -1 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:53 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 26.06.2022 14:38, Laurent Pinchart wrote:
>Hi Paul,
>
>Thank you for the patch.
>
>On Wed, Jun 15, 2022 at 04:11:25AM +0900, Paul Elder wrote:
>> On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
>> encoded in 34-bit. Shift them to the left by 2 bits so that they can be
>
>I think you meant right, not left.
>
>> contained in 32 bits.
>
>The important part here is that this is how the address is encoded in
>the hardware. I suppose it's obvious, otherwise it woudln't work at all,
>but maybe it could be explained more explicitly ?
>
>On the ISP that is integrated in the i.MX8MP, DMA addresses have been
>extended to 34 bits, with the 32 MSBs stored in the DMA address
>registers and the 2 LSBs set to 0. Shift the buffer addresses right by 2
>on that platform.

If the 32 MSB are all stored in the in the dma address then why do we
need to shift?
>
>> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>
>Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>> ---
>>  .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
>>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
>>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
>>  3 files changed, 14 insertions(+), 9 deletions(-)
>>
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>> index 35cec263c563..234b1f8488cb 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>> @@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
>>
>>  static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  {
>> +	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
>> +		   2 : 0;
>> +
>>  	cap->buf.curr = cap->buf.next;
>>  	cap->buf.next = NULL;
>>
>> @@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  		buff_addr = cap->buf.next->buff_addr;
>>
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
>> -			     buff_addr[RKISP1_PLANE_Y]);
>> +			     buff_addr[RKISP1_PLANE_Y] >> shift);
>>  		/*
>>  		 * In order to support grey format we capture
>>  		 * YUV422 planar format from the camera and
>> @@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cb_base_ad_init,
>> -				     cap->buf.dummy.dma_addr);
>> +				     cap->buf.dummy.dma_addr >> shift);
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cr_base_ad_init,
>> -				     cap->buf.dummy.dma_addr);
>> +				     cap->buf.dummy.dma_addr >> shift);
>>  		} else {
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cb_base_ad_init,
>> -				     buff_addr[RKISP1_PLANE_CB]);
>> +				     buff_addr[RKISP1_PLANE_CB] >> shift);
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cr_base_ad_init,
>> -				     buff_addr[RKISP1_PLANE_CR]);
>> +				     buff_addr[RKISP1_PLANE_CR] >> shift);
>>  		}
>>  	} else {
>>  		/*
>> @@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  		 * throw data if there is no available buffer.
>>  		 */
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
>> -			     cap->buf.dummy.dma_addr);
>> +			     cap->buf.dummy.dma_addr >> shift);
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
>> -			     cap->buf.dummy.dma_addr);
>> +			     cap->buf.dummy.dma_addr >> shift);
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
>> -			     cap->buf.dummy.dma_addr);
>> +			     cap->buf.dummy.dma_addr >> shift);
>>  	}
>>
>>  	/* Set plane offsets */
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> index 96657e55a5b0..0b834579d08c 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> @@ -113,6 +113,7 @@ enum rkisp1_feature {
>>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>>  	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
>> +	RKISP1_FEATURE_DMA_34BIT = BIT(4),

doc this field

thanks,
Dafna

>>  };
>>
>>  /*
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> index d68a805e8b6b..4c77aa2bc50a 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> @@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
>>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>>  	.isp_ver = IMX8MP_V10,
>>  	.features = RKISP1_FEATURE_RSZ_CROP
>> -		  | RKISP1_FEATURE_MAIN_STRIDE,
>> +		  | RKISP1_FEATURE_MAIN_STRIDE
>> +		  | RKISP1_FEATURE_DMA_34BIT,
>>  };
>>
>>  static const struct of_device_id rkisp1_of_match[] = {
>
>-- 
>Regards,
>
>Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
@ 2022-07-01  5:53       ` Dafna Hirschfeld
  0 siblings, 0 replies; 298+ messages in thread
From: Dafna Hirschfeld @ 2022-07-01  5:53 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

On 26.06.2022 14:38, Laurent Pinchart wrote:
>Hi Paul,
>
>Thank you for the patch.
>
>On Wed, Jun 15, 2022 at 04:11:25AM +0900, Paul Elder wrote:
>> On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
>> encoded in 34-bit. Shift them to the left by 2 bits so that they can be
>
>I think you meant right, not left.
>
>> contained in 32 bits.
>
>The important part here is that this is how the address is encoded in
>the hardware. I suppose it's obvious, otherwise it woudln't work at all,
>but maybe it could be explained more explicitly ?
>
>On the ISP that is integrated in the i.MX8MP, DMA addresses have been
>extended to 34 bits, with the 32 MSBs stored in the DMA address
>registers and the 2 LSBs set to 0. Shift the buffer addresses right by 2
>on that platform.

If the 32 MSB are all stored in the in the dma address then why do we
need to shift?
>
>> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
>
>Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>
>> ---
>>  .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
>>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
>>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
>>  3 files changed, 14 insertions(+), 9 deletions(-)
>>
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>> index 35cec263c563..234b1f8488cb 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
>> @@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
>>
>>  static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  {
>> +	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
>> +		   2 : 0;
>> +
>>  	cap->buf.curr = cap->buf.next;
>>  	cap->buf.next = NULL;
>>
>> @@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  		buff_addr = cap->buf.next->buff_addr;
>>
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
>> -			     buff_addr[RKISP1_PLANE_Y]);
>> +			     buff_addr[RKISP1_PLANE_Y] >> shift);
>>  		/*
>>  		 * In order to support grey format we capture
>>  		 * YUV422 planar format from the camera and
>> @@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cb_base_ad_init,
>> -				     cap->buf.dummy.dma_addr);
>> +				     cap->buf.dummy.dma_addr >> shift);
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cr_base_ad_init,
>> -				     cap->buf.dummy.dma_addr);
>> +				     cap->buf.dummy.dma_addr >> shift);
>>  		} else {
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cb_base_ad_init,
>> -				     buff_addr[RKISP1_PLANE_CB]);
>> +				     buff_addr[RKISP1_PLANE_CB] >> shift);
>>  			rkisp1_write(cap->rkisp1,
>>  				     cap->config->mi.cr_base_ad_init,
>> -				     buff_addr[RKISP1_PLANE_CR]);
>> +				     buff_addr[RKISP1_PLANE_CR] >> shift);
>>  		}
>>  	} else {
>>  		/*
>> @@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
>>  		 * throw data if there is no available buffer.
>>  		 */
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
>> -			     cap->buf.dummy.dma_addr);
>> +			     cap->buf.dummy.dma_addr >> shift);
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
>> -			     cap->buf.dummy.dma_addr);
>> +			     cap->buf.dummy.dma_addr >> shift);
>>  		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
>> -			     cap->buf.dummy.dma_addr);
>> +			     cap->buf.dummy.dma_addr >> shift);
>>  	}
>>
>>  	/* Set plane offsets */
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> index 96657e55a5b0..0b834579d08c 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
>> @@ -113,6 +113,7 @@ enum rkisp1_feature {
>>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
>>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
>>  	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
>> +	RKISP1_FEATURE_DMA_34BIT = BIT(4),

doc this field

thanks,
Dafna

>>  };
>>
>>  /*
>> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> index d68a805e8b6b..4c77aa2bc50a 100644
>> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
>> @@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
>>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
>>  	.isp_ver = IMX8MP_V10,
>>  	.features = RKISP1_FEATURE_RSZ_CROP
>> -		  | RKISP1_FEATURE_MAIN_STRIDE,
>> +		  | RKISP1_FEATURE_MAIN_STRIDE
>> +		  | RKISP1_FEATURE_DMA_34BIT,
>>  };
>>
>>  static const struct of_device_id rkisp1_of_match[] = {
>
>-- 
>Regards,
>
>Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
  2022-07-01  5:53       ` Dafna Hirschfeld
@ 2022-07-01  8:38         ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-01  8:38 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jul 01, 2022 at 08:53:42AM +0300, Dafna Hirschfeld wrote:
> On 26.06.2022 14:38, Laurent Pinchart wrote:
> > On Wed, Jun 15, 2022 at 04:11:25AM +0900, Paul Elder wrote:
> >> On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
> >> encoded in 34-bit. Shift them to the left by 2 bits so that they can be
> >
> > I think you meant right, not left.
> >
> >> contained in 32 bits.
> >
> > The important part here is that this is how the address is encoded in
> > the hardware. I suppose it's obvious, otherwise it woudln't work at all,
> > but maybe it could be explained more explicitly ?
> >
> > On the ISP that is integrated in the i.MX8MP, DMA addresses have been
> > extended to 34 bits, with the 32 MSBs stored in the DMA address
> > registers and the 2 LSBs set to 0. Shift the buffer addresses right by 2
> > on that platform.
> 
> If the 32 MSB are all stored in the in the dma address then why do we
> need to shift?

On Rokchip SoCs the DMA address is 32-bit wide, and stored as-is in the
registers. On i.MX8MP, the DMA address is 34-bit, and must be aligned to
a multiple of 4 bytes, so the two LSBs are guaranteed to be 0. The DMA
registers are still 32-bit wide, and store bits [33:2] of the DMA
addresses, hence the shift.

> >> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> >
> > Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >
> >> ---
> >>  .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
> >>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
> >>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
> >>  3 files changed, 14 insertions(+), 9 deletions(-)
> >>
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> >> index 35cec263c563..234b1f8488cb 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> >> @@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
> >>
> >>  static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  {
> >> +	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
> >> +		   2 : 0;
> >> +
> >>  	cap->buf.curr = cap->buf.next;
> >>  	cap->buf.next = NULL;
> >>
> >> @@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  		buff_addr = cap->buf.next->buff_addr;
> >>
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> >> -			     buff_addr[RKISP1_PLANE_Y]);
> >> +			     buff_addr[RKISP1_PLANE_Y] >> shift);
> >>  		/*
> >>  		 * In order to support grey format we capture
> >>  		 * YUV422 planar format from the camera and
> >> @@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cb_base_ad_init,
> >> -				     cap->buf.dummy.dma_addr);
> >> +				     cap->buf.dummy.dma_addr >> shift);
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cr_base_ad_init,
> >> -				     cap->buf.dummy.dma_addr);
> >> +				     cap->buf.dummy.dma_addr >> shift);
> >>  		} else {
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cb_base_ad_init,
> >> -				     buff_addr[RKISP1_PLANE_CB]);
> >> +				     buff_addr[RKISP1_PLANE_CB] >> shift);
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cr_base_ad_init,
> >> -				     buff_addr[RKISP1_PLANE_CR]);
> >> +				     buff_addr[RKISP1_PLANE_CR] >> shift);
> >>  		}
> >>  	} else {
> >>  		/*
> >> @@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  		 * throw data if there is no available buffer.
> >>  		 */
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> >> -			     cap->buf.dummy.dma_addr);
> >> +			     cap->buf.dummy.dma_addr >> shift);
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
> >> -			     cap->buf.dummy.dma_addr);
> >> +			     cap->buf.dummy.dma_addr >> shift);
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
> >> -			     cap->buf.dummy.dma_addr);
> >> +			     cap->buf.dummy.dma_addr >> shift);
> >>  	}
> >>
> >>  	/* Set plane offsets */
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >> index 96657e55a5b0..0b834579d08c 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >> @@ -113,6 +113,7 @@ enum rkisp1_feature {
> >>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> >>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
> >>  	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
> >> +	RKISP1_FEATURE_DMA_34BIT = BIT(4),
> 
> doc this field

Looks like only RKISP1_FEATURE_MIPI_CSI2 is documented. We'll fix that
in v3.

> >>  };
> >>
> >>  /*
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> index d68a805e8b6b..4c77aa2bc50a 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> @@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
> >>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> >>  	.isp_ver = IMX8MP_V10,
> >>  	.features = RKISP1_FEATURE_RSZ_CROP
> >> -		  | RKISP1_FEATURE_MAIN_STRIDE,
> >> +		  | RKISP1_FEATURE_MAIN_STRIDE
> >> +		  | RKISP1_FEATURE_DMA_34BIT,
> >>  };
> >>
> >>  static const struct of_device_id rkisp1_of_match[] = {

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP
@ 2022-07-01  8:38         ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-01  8:38 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jul 01, 2022 at 08:53:42AM +0300, Dafna Hirschfeld wrote:
> On 26.06.2022 14:38, Laurent Pinchart wrote:
> > On Wed, Jun 15, 2022 at 04:11:25AM +0900, Paul Elder wrote:
> >> On the ISP that is integrated in the i.MX8MP, the DMA base addresses are
> >> encoded in 34-bit. Shift them to the left by 2 bits so that they can be
> >
> > I think you meant right, not left.
> >
> >> contained in 32 bits.
> >
> > The important part here is that this is how the address is encoded in
> > the hardware. I suppose it's obvious, otherwise it woudln't work at all,
> > but maybe it could be explained more explicitly ?
> >
> > On the ISP that is integrated in the i.MX8MP, DMA addresses have been
> > extended to 34 bits, with the 32 MSBs stored in the DMA address
> > registers and the 2 LSBs set to 0. Shift the buffer addresses right by 2
> > on that platform.
> 
> If the 32 MSB are all stored in the in the dma address then why do we
> need to shift?

On Rokchip SoCs the DMA address is 32-bit wide, and stored as-is in the
registers. On i.MX8MP, the DMA address is 34-bit, and must be aligned to
a multiple of 4 bytes, so the two LSBs are guaranteed to be 0. The DMA
registers are still 32-bit wide, and store bits [33:2] of the DMA
addresses, hence the shift.

> >> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> >
> > Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >
> >> ---
> >>  .../platform/rockchip/rkisp1/rkisp1-capture.c | 19 +++++++++++--------
> >>  .../platform/rockchip/rkisp1/rkisp1-common.h  |  1 +
> >>  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  3 ++-
> >>  3 files changed, 14 insertions(+), 9 deletions(-)
> >>
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> >> index 35cec263c563..234b1f8488cb 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-capture.c
> >> @@ -624,6 +624,9 @@ static void rkisp1_dummy_buf_destroy(struct rkisp1_capture *cap)
> >>
> >>  static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  {
> >> +	u8 shift = cap->rkisp1->info->features & RKISP1_FEATURE_DMA_34BIT ?
> >> +		   2 : 0;
> >> +
> >>  	cap->buf.curr = cap->buf.next;
> >>  	cap->buf.next = NULL;
> >>
> >> @@ -636,7 +639,7 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  		buff_addr = cap->buf.next->buff_addr;
> >>
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> >> -			     buff_addr[RKISP1_PLANE_Y]);
> >> +			     buff_addr[RKISP1_PLANE_Y] >> shift);
> >>  		/*
> >>  		 * In order to support grey format we capture
> >>  		 * YUV422 planar format from the camera and
> >> @@ -645,17 +648,17 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  		if (cap->pix.cfg->fourcc == V4L2_PIX_FMT_GREY) {
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cb_base_ad_init,
> >> -				     cap->buf.dummy.dma_addr);
> >> +				     cap->buf.dummy.dma_addr >> shift);
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cr_base_ad_init,
> >> -				     cap->buf.dummy.dma_addr);
> >> +				     cap->buf.dummy.dma_addr >> shift);
> >>  		} else {
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cb_base_ad_init,
> >> -				     buff_addr[RKISP1_PLANE_CB]);
> >> +				     buff_addr[RKISP1_PLANE_CB] >> shift);
> >>  			rkisp1_write(cap->rkisp1,
> >>  				     cap->config->mi.cr_base_ad_init,
> >> -				     buff_addr[RKISP1_PLANE_CR]);
> >> +				     buff_addr[RKISP1_PLANE_CR] >> shift);
> >>  		}
> >>  	} else {
> >>  		/*
> >> @@ -663,11 +666,11 @@ static void rkisp1_set_next_buf(struct rkisp1_capture *cap)
> >>  		 * throw data if there is no available buffer.
> >>  		 */
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.y_base_ad_init,
> >> -			     cap->buf.dummy.dma_addr);
> >> +			     cap->buf.dummy.dma_addr >> shift);
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.cb_base_ad_init,
> >> -			     cap->buf.dummy.dma_addr);
> >> +			     cap->buf.dummy.dma_addr >> shift);
> >>  		rkisp1_write(cap->rkisp1, cap->config->mi.cr_base_ad_init,
> >> -			     cap->buf.dummy.dma_addr);
> >> +			     cap->buf.dummy.dma_addr >> shift);
> >>  	}
> >>
> >>  	/* Set plane offsets */
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >> index 96657e55a5b0..0b834579d08c 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> >> @@ -113,6 +113,7 @@ enum rkisp1_feature {
> >>  	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> >>  	RKISP1_FEATURE_RSZ_CROP = BIT(2),
> >>  	RKISP1_FEATURE_MAIN_STRIDE = BIT(3),
> >> +	RKISP1_FEATURE_DMA_34BIT = BIT(4),
> 
> doc this field

Looks like only RKISP1_FEATURE_MIPI_CSI2 is documented. We'll fix that
in v3.

> >>  };
> >>
> >>  /*
> >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> index d68a805e8b6b..4c77aa2bc50a 100644
> >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> >> @@ -506,7 +506,8 @@ static const struct rkisp1_info imx8mp_isp_info = {
> >>  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> >>  	.isp_ver = IMX8MP_V10,
> >>  	.features = RKISP1_FEATURE_RSZ_CROP
> >> -		  | RKISP1_FEATURE_MAIN_STRIDE,
> >> +		  | RKISP1_FEATURE_MAIN_STRIDE
> >> +		  | RKISP1_FEATURE_DMA_34BIT,
> >>  };
> >>
> >>  static const struct of_device_id rkisp1_of_match[] = {

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
  2022-07-01  5:22     ` Dafna Hirschfeld
@ 2022-07-01  9:19       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-01  9:19 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jul 01, 2022 at 08:22:22AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:11, Paul Elder wrote:
> > The rkisp1 can take an input on the parallel interface. Add a port for
> > it, and update the required field. At least one port is required, and
> > both may be specified.
> >
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
> >  1 file changed, 21 insertions(+), 2 deletions(-)
> >
> > diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> > index d1489b177331..b3661d7d4357 100644
> > --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> > +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> > @@ -84,8 +84,27 @@ properties:
> >                  minItems: 1
> >                  maxItems: 4
> > 
> > -    required:
> > -      - port@0
> > +      port@1:
> > +        $ref: /schemas/graph.yaml#/$defs/port-base
> > +        unevaluatedProperties: false
> > +        description: connection point for input on the parallel interface
> > +
> > +        properties:
> > +          bus-type:
> > +            enum: [5, 6]
> > +
> > +          endpoint:
> > +            $ref: video-interfaces.yaml#
> > +            unevaluatedProperties: false
> > +
> > +        required:
> > +          - bus-type
> > +
> > +    anyOf:
> > +      - required:
> > +          - port@0
> > +      - required:
> > +          - port@1
> > 
> >  required:
> >    - compatible
> 
> Could be nice to add an example

I don't have a real-life example of a parallel sensor connected to a
RK3399, but the i.MX8MP connects its CSI-2 receiver to the parallel
input of the ISP. I'll add an example to the other DT bindings patch
that adds the compatible string for the i.MX8MP, is that OK ?

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface
@ 2022-07-01  9:19       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-01  9:19 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jul 01, 2022 at 08:22:22AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:11, Paul Elder wrote:
> > The rkisp1 can take an input on the parallel interface. Add a port for
> > it, and update the required field. At least one port is required, and
> > both may be specified.
> >
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../bindings/media/rockchip-isp1.yaml         | 23 +++++++++++++++++--
> >  1 file changed, 21 insertions(+), 2 deletions(-)
> >
> > diff --git a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> > index d1489b177331..b3661d7d4357 100644
> > --- a/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> > +++ b/Documentation/devicetree/bindings/media/rockchip-isp1.yaml
> > @@ -84,8 +84,27 @@ properties:
> >                  minItems: 1
> >                  maxItems: 4
> > 
> > -    required:
> > -      - port@0
> > +      port@1:
> > +        $ref: /schemas/graph.yaml#/$defs/port-base
> > +        unevaluatedProperties: false
> > +        description: connection point for input on the parallel interface
> > +
> > +        properties:
> > +          bus-type:
> > +            enum: [5, 6]
> > +
> > +          endpoint:
> > +            $ref: video-interfaces.yaml#
> > +            unevaluatedProperties: false
> > +
> > +        required:
> > +          - bus-type
> > +
> > +    anyOf:
> > +      - required:
> > +          - port@0
> > +      - required:
> > +          - port@1
> > 
> >  required:
> >    - compatible
> 
> Could be nice to add an example

I don't have a real-life example of a parallel sensor connected to a
RK3399, but the i.MX8MP connects its CSI-2 receiver to the parallel
input of the ISP. I'll add an example to the other DT bindings patch
that adds the compatible string for the i.MX8MP, is that OK ?

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time
  2022-07-01  4:36     ` Dafna Hirschfeld
@ 2022-07-01 11:29       ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-01 11:29 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jul 01, 2022 at 07:36:41AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:10, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > When a sensor is bound, its source pad is retrieved in the .bound()
> > operation with a call to media_entity_get_fwnode_pad(). The function
> > should be called with the source endpoint fwnode of the sensor, but is
> > instead called with the sensor's device fwnode.
> > 
> > Fix this, which involves storing a reference to the source endpoint
> > fwnode in the rkisp1_sensor_async structure, and thus implementing the
> > subdev notifier .destroy() operation to release the reference.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 28 ++++++++++++++++---
> >  2 files changed, 26 insertions(+), 4 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index ba11baf75fa9..60c5462e1746 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -117,6 +117,7 @@ struct rkisp1_info {
> >   *
> >   * @asd:		async_subdev variable for the sensor
> >   * @index:		index of the sensor (counting sensor found in DT)
> > + * @source_ep:		fwnode for the sensor source endpoint
> >   * @lanes:		number of lanes
> >   * @mbus_type:		type of bus (currently only CSI2 is supported)
> >   * @mbus_flags:		media bus (V4L2_MBUS_*) flags
> > @@ -127,6 +128,7 @@ struct rkisp1_info {
> >  struct rkisp1_sensor_async {
> >  	struct v4l2_async_subdev asd;
> >  	unsigned int index;
> > +	struct fwnode_handle *source_ep;
> >  	unsigned int lanes;
> >  	enum v4l2_mbus_type mbus_type;
> >  	unsigned int mbus_flags;
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index 386c1c17aec2..0f3e45cdbf2a 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -138,7 +138,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  	phy_init(s_asd->dphy);
> > 
> >  	/* Create the link to the sensor. */
> > -	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
> > +	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> >  						 MEDIA_PAD_FL_SOURCE);
> >  	if (source_pad < 0) {
> >  		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
> > @@ -170,10 +170,19 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> >  	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
> >  }
> > 
> > +static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
> > +{
> > +	struct rkisp1_sensor_async *rk_asd =
> > +		container_of(asd, struct rkisp1_sensor_async, asd);
> > +
> > +	fwnode_handle_put(rk_asd->source_ep);
> > +}
> > +
> >  static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> >  	.bound = rkisp1_subdev_notifier_bound,
> >  	.unbind = rkisp1_subdev_notifier_unbind,
> >  	.complete = rkisp1_subdev_notifier_complete,
> > +	.destroy = rkisp1_subdev_notifier_destroy,
> >  };
> > 
> >  static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> > @@ -190,6 +199,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> >  			.bus_type = V4L2_MBUS_CSI2_DPHY
> >  		};
> >  		struct rkisp1_sensor_async *rk_asd;
> > +		struct fwnode_handle *source = NULL;
> >  		struct fwnode_handle *ep;
> > 
> >  		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
> > @@ -202,15 +212,24 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> >  		if (ret)
> >  			goto err_parse;
> > 
> > -		rk_asd = v4l2_async_nf_add_fwnode_remote(ntf, ep,
> > -							 struct
> > -							 rkisp1_sensor_async);
> > +		source = fwnode_graph_get_remote_endpoint(ep);
> > +		if (!source) {
> > +			dev_err(rkisp1->dev,
> > +				"endpoint %pfw has no remote endpoint\n",
> > +				ep);
> > +			ret = -ENODEV;
> > +			goto err_parse;
> > +		}
> > +
> > +		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
> > +						  struct rkisp1_sensor_async);
> >  		if (IS_ERR(rk_asd)) {
> >  			ret = PTR_ERR(rk_asd);
> >  			goto err_parse;
> >  		}
> > 
> >  		rk_asd->index = index++;
> > +		rk_asd->source_ep = source;
> 
> here do 'source = NULL', see reason below
> 
> >  		rk_asd->mbus_type = vep.bus_type;
> >  		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
> >  		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
> > @@ -225,6 +244,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> >  		continue;
> >  err_parse:
> >  		fwnode_handle_put(ep);
> > +		fwnode_handle_put(source);
> 
> if v4l2_fwnode_endpoint_parse fails then here you put the source of previous iteration

source is a variable local to the loop, and it's initialized to NULL in
the declaration, so it will be reset to NULL at every iteration.

> >  		v4l2_async_nf_cleanup(ntf);
> >  		return ret;
> >  	}

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time
@ 2022-07-01 11:29       ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-01 11:29 UTC (permalink / raw)
  To: Dafna Hirschfeld
  Cc: Paul Elder, linux-media, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Dafna,

On Fri, Jul 01, 2022 at 07:36:41AM +0300, Dafna Hirschfeld wrote:
> On 15.06.2022 04:10, Paul Elder wrote:
> > From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > 
> > When a sensor is bound, its source pad is retrieved in the .bound()
> > operation with a call to media_entity_get_fwnode_pad(). The function
> > should be called with the source endpoint fwnode of the sensor, but is
> > instead called with the sensor's device fwnode.
> > 
> > Fix this, which involves storing a reference to the source endpoint
> > fwnode in the rkisp1_sensor_async structure, and thus implementing the
> > subdev notifier .destroy() operation to release the reference.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 28 ++++++++++++++++---
> >  2 files changed, 26 insertions(+), 4 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index ba11baf75fa9..60c5462e1746 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -117,6 +117,7 @@ struct rkisp1_info {
> >   *
> >   * @asd:		async_subdev variable for the sensor
> >   * @index:		index of the sensor (counting sensor found in DT)
> > + * @source_ep:		fwnode for the sensor source endpoint
> >   * @lanes:		number of lanes
> >   * @mbus_type:		type of bus (currently only CSI2 is supported)
> >   * @mbus_flags:		media bus (V4L2_MBUS_*) flags
> > @@ -127,6 +128,7 @@ struct rkisp1_info {
> >  struct rkisp1_sensor_async {
> >  	struct v4l2_async_subdev asd;
> >  	unsigned int index;
> > +	struct fwnode_handle *source_ep;
> >  	unsigned int lanes;
> >  	enum v4l2_mbus_type mbus_type;
> >  	unsigned int mbus_flags;
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index 386c1c17aec2..0f3e45cdbf2a 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -138,7 +138,7 @@ static int rkisp1_subdev_notifier_bound(struct v4l2_async_notifier *notifier,
> >  	phy_init(s_asd->dphy);
> > 
> >  	/* Create the link to the sensor. */
> > -	source_pad = media_entity_get_fwnode_pad(&sd->entity, sd->fwnode,
> > +	source_pad = media_entity_get_fwnode_pad(&sd->entity, s_asd->source_ep,
> >  						 MEDIA_PAD_FL_SOURCE);
> >  	if (source_pad < 0) {
> >  		dev_err(rkisp1->dev, "failed to find source pad for %s\n",
> > @@ -170,10 +170,19 @@ static int rkisp1_subdev_notifier_complete(struct v4l2_async_notifier *notifier)
> >  	return v4l2_device_register_subdev_nodes(&rkisp1->v4l2_dev);
> >  }
> > 
> > +static void rkisp1_subdev_notifier_destroy(struct v4l2_async_subdev *asd)
> > +{
> > +	struct rkisp1_sensor_async *rk_asd =
> > +		container_of(asd, struct rkisp1_sensor_async, asd);
> > +
> > +	fwnode_handle_put(rk_asd->source_ep);
> > +}
> > +
> >  static const struct v4l2_async_notifier_operations rkisp1_subdev_notifier_ops = {
> >  	.bound = rkisp1_subdev_notifier_bound,
> >  	.unbind = rkisp1_subdev_notifier_unbind,
> >  	.complete = rkisp1_subdev_notifier_complete,
> > +	.destroy = rkisp1_subdev_notifier_destroy,
> >  };
> > 
> >  static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> > @@ -190,6 +199,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> >  			.bus_type = V4L2_MBUS_CSI2_DPHY
> >  		};
> >  		struct rkisp1_sensor_async *rk_asd;
> > +		struct fwnode_handle *source = NULL;
> >  		struct fwnode_handle *ep;
> > 
> >  		ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(rkisp1->dev),
> > @@ -202,15 +212,24 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> >  		if (ret)
> >  			goto err_parse;
> > 
> > -		rk_asd = v4l2_async_nf_add_fwnode_remote(ntf, ep,
> > -							 struct
> > -							 rkisp1_sensor_async);
> > +		source = fwnode_graph_get_remote_endpoint(ep);
> > +		if (!source) {
> > +			dev_err(rkisp1->dev,
> > +				"endpoint %pfw has no remote endpoint\n",
> > +				ep);
> > +			ret = -ENODEV;
> > +			goto err_parse;
> > +		}
> > +
> > +		rk_asd = v4l2_async_nf_add_fwnode(ntf, source,
> > +						  struct rkisp1_sensor_async);
> >  		if (IS_ERR(rk_asd)) {
> >  			ret = PTR_ERR(rk_asd);
> >  			goto err_parse;
> >  		}
> > 
> >  		rk_asd->index = index++;
> > +		rk_asd->source_ep = source;
> 
> here do 'source = NULL', see reason below
> 
> >  		rk_asd->mbus_type = vep.bus_type;
> >  		rk_asd->mbus_flags = vep.bus.mipi_csi2.flags;
> >  		rk_asd->lanes = vep.bus.mipi_csi2.num_data_lanes;
> > @@ -225,6 +244,7 @@ static int rkisp1_subdev_notifier_register(struct rkisp1_device *rkisp1)
> >  		continue;
> >  err_parse:
> >  		fwnode_handle_put(ep);
> > +		fwnode_handle_put(source);
> 
> if v4l2_fwnode_endpoint_parse fails then here you put the source of previous iteration

source is a variable local to the loop, and it's initialized to NULL in
the declaration, so it will be reset to NULL at every iteration.

> >  		v4l2_async_nf_cleanup(ntf);
> >  		return ret;
> >  	}

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
  2022-06-25 17:59       ` Laurent Pinchart
@ 2022-07-04  3:46         ` paul.elder
  -1 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04  3:46 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Laurent,

Sorry for the delay.

On Sat, Jun 25, 2022 at 08:59:48PM +0300, Laurent Pinchart wrote:
> Hi Paul,
> 
> On Thu, Jun 16, 2022 at 01:41:56AM +0300, Laurent Pinchart wrote:
> > On Wed, Jun 15, 2022 at 04:10:33AM +0900, Paul Elder wrote:
> > > Add a register dump file in debugfs for some of the buffer-related
> > > registers in MI, for the base address, the size, and the offset. Also
> > > dump the appropriate shadow registers.
> > > 
> > > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > > ---
> > >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
> > >  1 file changed, 21 insertions(+)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > > index e76dc2b164b6..1a59c00fabdd 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > > @@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> > >  }
> > >  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
> > >  
> > > +static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
> > > +{
> > > +	static const struct rkisp1_debug_register registers[] = {
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
> > > +		{ /* Sentinel */ },
> > > +	};
> > > +	struct rkisp1_device *rkisp1 = m->private;
> > > +
> > > +	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
> > > +}
> > > +DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
> > > +
> > >  #define RKISP1_DEBUG_DATA_COUNT_BINS	32
> > >  #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
> > >  
> > > @@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
> > >  	debugfs_create_file("srsz", 0444, regs_dir,
> > >  			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
> > >  			    &rkisp1_debug_dump_rsz_regs_fops);
> > > +
> > > +	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
> > > +			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);
> > 
> > That's a very specialized file. I wonder if we should call it just
> > "mi_mp" if it needs to be extended later with other memory interface
> > registers for the main path. Or maybe even just "mi", to cover the self
> > path too ? The latter may be a tad too generic. What do you think ?

I think mi_mp would be good. imo mi might be a tad too generic and get
crowded with the self path registers (probably).


Paul

> 
> Ping
>
> 
> > >  }
> > >  
> > >  void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers
@ 2022-07-04  3:46         ` paul.elder
  0 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04  3:46 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Laurent,

Sorry for the delay.

On Sat, Jun 25, 2022 at 08:59:48PM +0300, Laurent Pinchart wrote:
> Hi Paul,
> 
> On Thu, Jun 16, 2022 at 01:41:56AM +0300, Laurent Pinchart wrote:
> > On Wed, Jun 15, 2022 at 04:10:33AM +0900, Paul Elder wrote:
> > > Add a register dump file in debugfs for some of the buffer-related
> > > registers in MI, for the base address, the size, and the offset. Also
> > > dump the appropriate shadow registers.
> > > 
> > > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > > ---
> > >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 21 +++++++++++++++++++
> > >  1 file changed, 21 insertions(+)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > > index e76dc2b164b6..1a59c00fabdd 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > > @@ -121,6 +121,24 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> > >  }
> > >  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
> > >  
> > > +static int rkisp1_debug_dump_mi_mp_y_offs_cnt_show(struct seq_file *m, void *p)
> > > +{
> > > +	static const struct rkisp1_debug_register registers[] = {
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_INIT2),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_BASE_AD_SHD),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_INIT),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_SIZE_SHD),
> > > +		RKISP1_DEBUG_REG(MI_MP_Y_OFFS_CNT_SHD),
> > > +		{ /* Sentinel */ },
> > > +	};
> > > +	struct rkisp1_device *rkisp1 = m->private;
> > > +
> > > +	return rkisp1_debug_dump_regs(rkisp1, m, 0, registers);
> > > +}
> > > +DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_mi_mp_y_offs_cnt);
> > > +
> > >  #define RKISP1_DEBUG_DATA_COUNT_BINS	32
> > >  #define RKISP1_DEBUG_DATA_COUNT_STEP	(4096 / RKISP1_DEBUG_DATA_COUNT_BINS)
> > >  
> > > @@ -214,6 +232,9 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
> > >  	debugfs_create_file("srsz", 0444, regs_dir,
> > >  			    &rkisp1->resizer_devs[RKISP1_SELFPATH],
> > >  			    &rkisp1_debug_dump_rsz_regs_fops);
> > > +
> > > +	debugfs_create_file("mi_mp_y_bufs", 0444, regs_dir, rkisp1,
> > > +			    &rkisp1_debug_dump_mi_mp_y_offs_cnt_fops);
> > 
> > That's a very specialized file. I wonder if we should call it just
> > "mi_mp" if it needs to be extended later with other memory interface
> > registers for the main path. Or maybe even just "mi", to cover the self
> > path too ? The latter may be a tad too generic. What do you think ?

I think mi_mp would be good. imo mi might be a tad too generic and get
crowded with the self path registers (probably).


Paul

> 
> Ping
>
> 
> > >  }
> > >  
> > >  void rkisp1_debug_cleanup(struct rkisp1_device *rkisp1)

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts
  2022-06-16  0:44     ` Laurent Pinchart
@ 2022-07-04  3:47       ` paul.elder
  -1 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04  3:47 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Laurent,

On Thu, Jun 16, 2022 at 03:44:23AM +0300, Laurent Pinchart wrote:
> Hi Paul,
> 
> Thank you for the patch.
> 
> On Wed, Jun 15, 2022 at 04:10:35AM +0900, Paul Elder wrote:
> > Add files in debugfs to monitor some of the interrupts of the MI and
> > ISP. Add the appropriate holder variables in the rkisp1_debug struct as
> > well.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  9 +++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 20 +++++++++++++++++++
> >  2 files changed, 29 insertions(+)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index 4243ff5e2197..a67fe7b1dfa1 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -364,6 +364,15 @@ struct rkisp1_debug {
> >  	unsigned long stats_error;
> >  	unsigned long stop_timeout[2];
> >  	unsigned long frame_drop[2];
> > +	unsigned long mi_irq_mblk_line_count;
> > +	unsigned long mi_irq_fill_mp_y_count;
> > +	unsigned long mi_irq_frame_count;
> > +	unsigned long mi_irq_wrap_mp_y_count;
> > +	unsigned long mi_irq_wrap_mp_cb_count;
> > +	unsigned long mi_irq_wrap_mp_cr_count;
> > +	unsigned long isp_irq_v_start_count;
> > +	unsigned long isp_irq_frame_count;
> > +	unsigned long isp_irq_frame_in_count;
> >  };
> >  
> >  /*
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > index 1a59c00fabdd..02854e8ea1a4 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > @@ -220,6 +220,26 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
> >  	debugfs_create_file("input_status", 0444, debug->debugfs_dir, rkisp1,
> >  			    &rkisp1_debug_input_status_fops);
> >  
> > +	debugfs_create_ulong("mi_irq_mblk_line_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_mblk_line_count);
> > +	debugfs_create_ulong("mi_irq_fill_mp_y_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_fill_mp_y_count);
> > +	debugfs_create_ulong("mi_irq_frame_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_frame_count);
> > +	debugfs_create_ulong("mi_irq_wrap_mp_y_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_wrap_mp_y_count);
> > +	debugfs_create_ulong("mi_irq_wrap_mp_cb_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_wrap_mp_cb_count);
> > +	debugfs_create_ulong("mi_irq_wrap_mp_cr_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_wrap_mp_cr_count);
> > +
> > +	debugfs_create_ulong("isp_irq_v_start_count", 0444, debug->debugfs_dir,
> > +			     &debug->isp_irq_v_start_count);
> > +	debugfs_create_ulong("isp_irq_frame_count", 0444, debug->debugfs_dir,
> > +			     &debug->isp_irq_frame_count);
> > +	debugfs_create_ulong("isp_irq_frame_in_count", 0444, debug->debugfs_dir,
> > +			     &debug->isp_irq_frame_in_count);
> 
> It's nice to expose these through debugfs, but it looks like you never
> actually set any of those fields :-) I think you could just drop this
> patch.

Oops, you're right :p

Yeah we can drop it.


Paul

> 
> > +
> >  	regs_dir = debugfs_create_dir("regs", debug->debugfs_dir);
> >  
> >  	debugfs_create_file("core", 0444, regs_dir, rkisp1,

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts
@ 2022-07-04  3:47       ` paul.elder
  0 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04  3:47 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Laurent,

On Thu, Jun 16, 2022 at 03:44:23AM +0300, Laurent Pinchart wrote:
> Hi Paul,
> 
> Thank you for the patch.
> 
> On Wed, Jun 15, 2022 at 04:10:35AM +0900, Paul Elder wrote:
> > Add files in debugfs to monitor some of the interrupts of the MI and
> > ISP. Add the appropriate holder variables in the rkisp1_debug struct as
> > well.
> > 
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  9 +++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 20 +++++++++++++++++++
> >  2 files changed, 29 insertions(+)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index 4243ff5e2197..a67fe7b1dfa1 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -364,6 +364,15 @@ struct rkisp1_debug {
> >  	unsigned long stats_error;
> >  	unsigned long stop_timeout[2];
> >  	unsigned long frame_drop[2];
> > +	unsigned long mi_irq_mblk_line_count;
> > +	unsigned long mi_irq_fill_mp_y_count;
> > +	unsigned long mi_irq_frame_count;
> > +	unsigned long mi_irq_wrap_mp_y_count;
> > +	unsigned long mi_irq_wrap_mp_cb_count;
> > +	unsigned long mi_irq_wrap_mp_cr_count;
> > +	unsigned long isp_irq_v_start_count;
> > +	unsigned long isp_irq_frame_count;
> > +	unsigned long isp_irq_frame_in_count;
> >  };
> >  
> >  /*
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > index 1a59c00fabdd..02854e8ea1a4 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > @@ -220,6 +220,26 @@ void rkisp1_debug_init(struct rkisp1_device *rkisp1)
> >  	debugfs_create_file("input_status", 0444, debug->debugfs_dir, rkisp1,
> >  			    &rkisp1_debug_input_status_fops);
> >  
> > +	debugfs_create_ulong("mi_irq_mblk_line_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_mblk_line_count);
> > +	debugfs_create_ulong("mi_irq_fill_mp_y_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_fill_mp_y_count);
> > +	debugfs_create_ulong("mi_irq_frame_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_frame_count);
> > +	debugfs_create_ulong("mi_irq_wrap_mp_y_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_wrap_mp_y_count);
> > +	debugfs_create_ulong("mi_irq_wrap_mp_cb_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_wrap_mp_cb_count);
> > +	debugfs_create_ulong("mi_irq_wrap_mp_cr_count", 0444, debug->debugfs_dir,
> > +			     &debug->mi_irq_wrap_mp_cr_count);
> > +
> > +	debugfs_create_ulong("isp_irq_v_start_count", 0444, debug->debugfs_dir,
> > +			     &debug->isp_irq_v_start_count);
> > +	debugfs_create_ulong("isp_irq_frame_count", 0444, debug->debugfs_dir,
> > +			     &debug->isp_irq_frame_count);
> > +	debugfs_create_ulong("isp_irq_frame_in_count", 0444, debug->debugfs_dir,
> > +			     &debug->isp_irq_frame_in_count);
> 
> It's nice to expose these through debugfs, but it looks like you never
> actually set any of those fields :-) I think you could just drop this
> patch.

Oops, you're right :p

Yeah we can drop it.


Paul

> 
> > +
> >  	regs_dir = debugfs_create_dir("regs", debug->debugfs_dir);
> >  
> >  	debugfs_create_file("core", 0444, regs_dir, rkisp1,

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
  2022-06-26 11:07         ` Laurent Pinchart
@ 2022-07-04 10:36           ` paul.elder
  -1 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04 10:36 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Dafna Hirschfeld, linux-media, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello,

On Sun, Jun 26, 2022 at 02:07:22PM +0300, Laurent Pinchart wrote:
> On Sun, Jun 26, 2022 at 07:05:43AM +0300, Dafna Hirschfeld wrote:
> > On 18.06.2022 02:26, Laurent Pinchart wrote:
> > > On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
> > >> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
> > >>
> > >> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > >> ---
> > >>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
> > >>  include/uapi/linux/rkisp1-config.h            |  3 +++
> > >>  2 files changed, 25 insertions(+)
> > >>
> > >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > >> index 62fa2bd275fe..3a0115bdcee5 100644
> > >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > >> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
> > >>  	.features = RKISP1_FEATURE_MIPI_CSI2,
> > >>  };
> > >>
> > >> +static const char * const imx8mp_isp_clks[] = {
> > >> +	"isp",
> > >> +	"hclk",
> > >> +	"aclk",
> > >> +};
> > >> +
> > >> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
> > >> +	{ NULL, rkisp1_isr },
> > >> +};
> > >> +
> > >> +static const struct rkisp1_info imx8mp_isp_info = {
> > >> +	.clks = imx8mp_isp_clks,
> > >> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
> > >> +	.isrs = imx8mp_isp_isrs,
> > >> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> > >> +	.isp_ver = IMX8MP_V10,
> > >> +};
> > >> +
> > >>  static const struct of_device_id rkisp1_of_match[] = {
> > >>  	{
> > >>  		.compatible = "rockchip,px30-cif-isp",
> > >> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
> > >>  		.compatible = "rockchip,rk3399-cif-isp",
> > >>  		.data = &rk3399_isp_info,
> > >>  	},
> > >> +	{
> > >> +		.compatible = "fsl,imx8mp-isp",
> > >> +		.data = &imx8mp_isp_info,
> > >> +	},
> > >>  	{},
> > >>  };
> > >>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
> > >> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
> > >> index 583ca0d9a79d..40677d47825c 100644
> > >> --- a/include/uapi/linux/rkisp1-config.h
> > >> +++ b/include/uapi/linux/rkisp1-config.h
> > >> @@ -140,12 +140,15 @@
> > >>   * @RKISP1_V11: declared in the original vendor code, but not used
> > >>   * @RKISP1_V12: used at least in rk3326 and px30
> > >>   * @RKISP1_V13: used at least in rk1808
> > >> + * @IMX8MP_V10: used in at least imx8mp
> > >>   */
> > >>  enum rkisp1_cif_isp_version {
> > >>  	RKISP1_V10 = 10,
> > >>  	RKISP1_V11,
> > >>  	RKISP1_V12,
> > >>  	RKISP1_V13,
> > >> +	/* TODO Choose a better version for this */
> > >> +	IMX8MP_V10,
> > >
> > > Time to address this ? :-)
> > >
> > > Does anyone know where the current versioning scheme come from ?
> > 
> > It was added by Heiko Stübner, basically trying to figure out the
> > versions from the vedor code,
> > see https://lore.kernel.org/all/20210121144407.9045-6-dafna.hirschfeld@collabora.com/
> 
> Is that public code ? Heiko, do you have any pointer to it ?
> 
> As far as I understand, this ISP IP has been forked, and is now
> developed in parallel by Rockchip (for their own SoCs) and by
> VeriSilicon (under the name of ISP8000Nano). The versioning schemes on
> the two sides are different, and may have common roots. The fact that
> the ISP8000Nano can be customized at synthesis time also complicates
> this.
> 
> The question at hand is how to expose a single coherent versioning
> scheme to userspace in this driver. The hardware has a version
> identification register that we could use, but I don't know if it gives
> us enough information (as in guaranteeing that the same version value
> won't be used for different IP versions that would need to be
> distinguished from each other in userspace). The fact that Rockchip and
> VeriSilicon probably develop their own new versions without cooperating
> increases the risk of collision.
> 
> We will also have to tackle the question of UABI. Newer ISP versions
> will require extensions to the ISP parameters structure. The i.MX8MP has
> extra processing blocks that are not supported by the driver today. One
> option would be to duplicate the top-level rkisp1_params_cfg structure
> per ISP version, as well as a set of lower-level structure where
> appropriate (how to handle that easily and efficiently on the driver
> side will be interesting to figure out). Another option is to only add
> parameters to the end of the rkisp1_params_cfg structure, but I fear
> that won't scale. We'll end up with a large structure where lots of data
> will be irrelevant for any particular ISP version, and that will be
> error-prone.
> 
> Comments and idea will be appreciated.

Thinking out loud:

The most sure way is clearly to have feature flags for each feature.
Maybe one set of internal ones that only affect the driver, and another
set for userspace to see what the hardware is capable of. On the other
hand, from the top of my head, the ones that userspace cares about could
be probed in other ways, like the presence of the self path can be
obtained from the media graph, and available controls/formats from...
the list of available controls/formats.

Also if we have flags then... what's the point of the version number? Is
there any value in letting userspace know some version number if it
doesn't particularly correlate with the actual features that are
available? Plus, we run the risk of version numbers (from the version
register) colliding between VeriSilicon and Rockchip. Plus my
understanding is that the current version number that we have right now
(V10 ~ V13) is fairly arbitrary anyway? (but we have to keep it for
compatibility reasons.)

So...

1 - Do we need a precise version number for the purpose of probing
capabilities? Can it just be replaced with feature flags?
2 - Do we need feature flags? Can all information (that userspace cares
about be obtained by some other source? (I guess this needs more
investigation)
3 - Maybe userspace doesn't care about the precise version number at
all? We could just continue with an aribitrary version number (like
IMX_V10)?
4 - Or we could just expand the version number with what we get from the
version register? And have different... labels (?) based on the vendor?

Lots of thinking out loud with no clear conclusion :D


Paul

> 
> > >>  };
> > >>
> > >>  enum rkisp1_cif_isp_histogram_mode {

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP
@ 2022-07-04 10:36           ` paul.elder
  0 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04 10:36 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Dafna Hirschfeld, linux-media, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hello,

On Sun, Jun 26, 2022 at 02:07:22PM +0300, Laurent Pinchart wrote:
> On Sun, Jun 26, 2022 at 07:05:43AM +0300, Dafna Hirschfeld wrote:
> > On 18.06.2022 02:26, Laurent Pinchart wrote:
> > > On Wed, Jun 15, 2022 at 04:11:20AM +0900, Paul Elder wrote:
> > >> Add match data to the rkisp1 driver to match the i.MX8MP ISP.
> > >>
> > >> Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > >> ---
> > >>  .../platform/rockchip/rkisp1/rkisp1-dev.c     | 22 +++++++++++++++++++
> > >>  include/uapi/linux/rkisp1-config.h            |  3 +++
> > >>  2 files changed, 25 insertions(+)
> > >>
> > >> diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > >> index 62fa2bd275fe..3a0115bdcee5 100644
> > >> --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > >> +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > >> @@ -486,6 +486,24 @@ static const struct rkisp1_info rk3399_isp_info = {
> > >>  	.features = RKISP1_FEATURE_MIPI_CSI2,
> > >>  };
> > >>
> > >> +static const char * const imx8mp_isp_clks[] = {
> > >> +	"isp",
> > >> +	"hclk",
> > >> +	"aclk",
> > >> +};
> > >> +
> > >> +static const struct rkisp1_isr_data imx8mp_isp_isrs[] = {
> > >> +	{ NULL, rkisp1_isr },
> > >> +};
> > >> +
> > >> +static const struct rkisp1_info imx8mp_isp_info = {
> > >> +	.clks = imx8mp_isp_clks,
> > >> +	.clk_size = ARRAY_SIZE(imx8mp_isp_clks),
> > >> +	.isrs = imx8mp_isp_isrs,
> > >> +	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> > >> +	.isp_ver = IMX8MP_V10,
> > >> +};
> > >> +
> > >>  static const struct of_device_id rkisp1_of_match[] = {
> > >>  	{
> > >>  		.compatible = "rockchip,px30-cif-isp",
> > >> @@ -495,6 +513,10 @@ static const struct of_device_id rkisp1_of_match[] = {
> > >>  		.compatible = "rockchip,rk3399-cif-isp",
> > >>  		.data = &rk3399_isp_info,
> > >>  	},
> > >> +	{
> > >> +		.compatible = "fsl,imx8mp-isp",
> > >> +		.data = &imx8mp_isp_info,
> > >> +	},
> > >>  	{},
> > >>  };
> > >>  MODULE_DEVICE_TABLE(of, rkisp1_of_match);
> > >> diff --git a/include/uapi/linux/rkisp1-config.h b/include/uapi/linux/rkisp1-config.h
> > >> index 583ca0d9a79d..40677d47825c 100644
> > >> --- a/include/uapi/linux/rkisp1-config.h
> > >> +++ b/include/uapi/linux/rkisp1-config.h
> > >> @@ -140,12 +140,15 @@
> > >>   * @RKISP1_V11: declared in the original vendor code, but not used
> > >>   * @RKISP1_V12: used at least in rk3326 and px30
> > >>   * @RKISP1_V13: used at least in rk1808
> > >> + * @IMX8MP_V10: used in at least imx8mp
> > >>   */
> > >>  enum rkisp1_cif_isp_version {
> > >>  	RKISP1_V10 = 10,
> > >>  	RKISP1_V11,
> > >>  	RKISP1_V12,
> > >>  	RKISP1_V13,
> > >> +	/* TODO Choose a better version for this */
> > >> +	IMX8MP_V10,
> > >
> > > Time to address this ? :-)
> > >
> > > Does anyone know where the current versioning scheme come from ?
> > 
> > It was added by Heiko Stübner, basically trying to figure out the
> > versions from the vedor code,
> > see https://lore.kernel.org/all/20210121144407.9045-6-dafna.hirschfeld@collabora.com/
> 
> Is that public code ? Heiko, do you have any pointer to it ?
> 
> As far as I understand, this ISP IP has been forked, and is now
> developed in parallel by Rockchip (for their own SoCs) and by
> VeriSilicon (under the name of ISP8000Nano). The versioning schemes on
> the two sides are different, and may have common roots. The fact that
> the ISP8000Nano can be customized at synthesis time also complicates
> this.
> 
> The question at hand is how to expose a single coherent versioning
> scheme to userspace in this driver. The hardware has a version
> identification register that we could use, but I don't know if it gives
> us enough information (as in guaranteeing that the same version value
> won't be used for different IP versions that would need to be
> distinguished from each other in userspace). The fact that Rockchip and
> VeriSilicon probably develop their own new versions without cooperating
> increases the risk of collision.
> 
> We will also have to tackle the question of UABI. Newer ISP versions
> will require extensions to the ISP parameters structure. The i.MX8MP has
> extra processing blocks that are not supported by the driver today. One
> option would be to duplicate the top-level rkisp1_params_cfg structure
> per ISP version, as well as a set of lower-level structure where
> appropriate (how to handle that easily and efficiently on the driver
> side will be interesting to figure out). Another option is to only add
> parameters to the end of the rkisp1_params_cfg structure, but I fear
> that won't scale. We'll end up with a large structure where lots of data
> will be irrelevant for any particular ISP version, and that will be
> error-prone.
> 
> Comments and idea will be appreciated.

Thinking out loud:

The most sure way is clearly to have feature flags for each feature.
Maybe one set of internal ones that only affect the driver, and another
set for userspace to see what the hardware is capable of. On the other
hand, from the top of my head, the ones that userspace cares about could
be probed in other ways, like the presence of the self path can be
obtained from the media graph, and available controls/formats from...
the list of available controls/formats.

Also if we have flags then... what's the point of the version number? Is
there any value in letting userspace know some version number if it
doesn't particularly correlate with the actual features that are
available? Plus, we run the risk of version numbers (from the version
register) colliding between VeriSilicon and Rockchip. Plus my
understanding is that the current version number that we have right now
(V10 ~ V13) is fairly arbitrary anyway? (but we have to keep it for
compatibility reasons.)

So...

1 - Do we need a precise version number for the purpose of probing
capabilities? Can it just be replaced with feature flags?
2 - Do we need feature flags? Can all information (that userspace cares
about be obtained by some other source? (I guess this needs more
investigation)
3 - Maybe userspace doesn't care about the precise version number at
all? We could just continue with an aribitrary version number (like
IMX_V10)?
4 - Or we could just expand the version number with what we get from the
version register? And have different... labels (?) based on the vendor?

Lots of thinking out loud with no clear conclusion :D


Paul

> 
> > >>  };
> > >>
> > >>  enum rkisp1_cif_isp_histogram_mode {

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
  2022-06-26 11:59     ` Laurent Pinchart
@ 2022-07-04 10:37       ` paul.elder
  -1 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04 10:37 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Laurent,

On Sun, Jun 26, 2022 at 02:59:00PM +0300, Laurent Pinchart wrote:
> Hi Paul,
> 
> Thank you for the patch.
> 
> On Wed, Jun 15, 2022 at 04:11:22AM +0900, Paul Elder wrote:
> > The ISP version in the i.MX8MP has a separate set of registers for crop
> > that is currently not handled. Add a feature flag to determine which
> > type of crop the ISP supports and set the crop registers based on that.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
> >  .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
> >  5 files changed, 46 insertions(+), 5 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index 667fca0fef95..e4f422bed09a 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
> >   */
> >  enum rkisp1_feature {
> >  	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
> > +	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> > +	RKISP1_FEATURE_RSZ_CROP = BIT(2),
> >  };
> >  
> >  /*
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > index 02854e8ea1a4..753abd024ce7 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > @@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> >  		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
> >  		{ /* Sentinel */ },
> >  	};
> > +	static const struct rkisp1_debug_register crop_registers[] = {
> > +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
> > +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
> > +		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
> > +		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
> > +		{ /* Sentinel */ },
> > +	};
> >  	struct rkisp1_resizer *rsz = m->private;
> >  
> > -	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> > +	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> > +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
> > +		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
> > +				       crop_registers);
> > +
> > +	return 0;
> >  }
> >  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
> >  
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index a4496ee2e9b4..5abe33f5fed4 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
> >  	.isrs = px30_isp_isrs,
> >  	.isr_size = ARRAY_SIZE(px30_isp_isrs),
> >  	.isp_ver = RKISP1_V12,
> > -	.features = RKISP1_FEATURE_MIPI_CSI2,
> > +	.features = RKISP1_FEATURE_MIPI_CSI2
> > +		  | RKISP1_FEATURE_DUAL_CROP,
> >  };
> >  
> >  static const char * const rk3399_isp_clks[] = {
> > @@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
> >  	.isrs = rk3399_isp_isrs,
> >  	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
> >  	.isp_ver = RKISP1_V10,
> > -	.features = RKISP1_FEATURE_MIPI_CSI2,
> > +	.features = RKISP1_FEATURE_MIPI_CSI2
> > +		  | RKISP1_FEATURE_DUAL_CROP,
> >  };
> >  
> >  static const char * const imx8mp_isp_clks[] = {
> > @@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
> >  	.isrs = imx8mp_isp_isrs,
> >  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> >  	.isp_ver = IMX8MP_V10,
> > +	.features = RKISP1_FEATURE_RSZ_CROP,
> >  };
> >  
> >  static const struct of_device_id rkisp1_of_match[] = {
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > index dd3e6c38be67..1fc54ab22b6d 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > @@ -168,6 +168,9 @@
> >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> >  
> > +/* RSZ_CROP_[XY]_DIR */
> > +#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > +
> >  /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
> >  #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
> >  #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
> > @@ -926,6 +929,12 @@
> >  #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
> >  #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
> >  #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
> > +#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
> > +#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
> > +#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
> > +#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
> > +#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
> > +#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
> >  
> >  #define RKISP1_CIF_MI_BASE			0x00001400
> >  #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > index f4caa8f684aa..08bf3aa8088f 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > @@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
> >  {
> >  	u32 ratio, rsz_ctrl = 0;
> >  	unsigned int i;
> > +	u32 val;
> >  
> >  	/* No phase offset */
> >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
> > @@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
> >  
> >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
> >  
> > +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
> > +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
> > +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
> > +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
> > +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
> > +
> > +		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
> > +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
> > +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;
> 
> Shouldn't this depend on the input and output formats of the resizer ?

Oops, yeah it should.


Paul

> 
> > +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
> > +	}
> > +
> >  	rkisp1_rsz_update_shadow(rsz, when);
> >  }
> >  
> > @@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
> >  	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
> >  
> >  	if (!enable) {
> > -		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> > +		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> > +			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> >  		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> >  		return 0;
> >  	}
> > @@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
> >  
> >  	mutex_lock(&rsz->ops_lock);
> >  	rkisp1_rsz_config(rsz, when);
> > -	rkisp1_dcrop_config(rsz);
> > +	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> > +		rkisp1_dcrop_config(rsz);
> >  
> >  	mutex_unlock(&rsz->ops_lock);
> >  	return 0;

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP
@ 2022-07-04 10:37       ` paul.elder
  0 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04 10:37 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: linux-media, dafna, heiko, jeanmichel.hautbois, jacopo,
	djrscally, helen.koike, linux-rockchip

Hi Laurent,

On Sun, Jun 26, 2022 at 02:59:00PM +0300, Laurent Pinchart wrote:
> Hi Paul,
> 
> Thank you for the patch.
> 
> On Wed, Jun 15, 2022 at 04:11:22AM +0900, Paul Elder wrote:
> > The ISP version in the i.MX8MP has a separate set of registers for crop
> > that is currently not handled. Add a feature flag to determine which
> > type of crop the ISP supports and set the crop registers based on that.
> > 
> > Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > ---
> >  .../platform/rockchip/rkisp1/rkisp1-common.h  |  2 ++
> >  .../platform/rockchip/rkisp1/rkisp1-debug.c   | 14 +++++++++++++-
> >  .../platform/rockchip/rkisp1/rkisp1-dev.c     |  7 +++++--
> >  .../platform/rockchip/rkisp1/rkisp1-regs.h    |  9 +++++++++
> >  .../platform/rockchip/rkisp1/rkisp1-resizer.c | 19 +++++++++++++++++--
> >  5 files changed, 46 insertions(+), 5 deletions(-)
> > 
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > index 667fca0fef95..e4f422bed09a 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-common.h
> > @@ -110,6 +110,8 @@ enum rkisp1_isp_pad {
> >   */
> >  enum rkisp1_feature {
> >  	RKISP1_FEATURE_MIPI_CSI2 = BIT(0),
> > +	RKISP1_FEATURE_DUAL_CROP = BIT(1),
> > +	RKISP1_FEATURE_RSZ_CROP = BIT(2),
> >  };
> >  
> >  /*
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > index 02854e8ea1a4..753abd024ce7 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-debug.c
> > @@ -115,9 +115,21 @@ static int rkisp1_debug_dump_rsz_regs_show(struct seq_file *m, void *p)
> >  		RKISP1_DEBUG_SHD_REG(RSZ_PHASE_VC),
> >  		{ /* Sentinel */ },
> >  	};
> > +	static const struct rkisp1_debug_register crop_registers[] = {
> > +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_X_DIR),
> > +		RKISP1_DEBUG_SHD_REG(RSZ_CROP_Y_DIR),
> > +		RKISP1_DEBUG_REG(RSZ_FRAME_RATE),
> > +		RKISP1_DEBUG_REG(RSZ_FORMAT_CONV_CTRL),
> > +		{ /* Sentinel */ },
> > +	};
> >  	struct rkisp1_resizer *rsz = m->private;
> >  
> > -	return rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> > +	rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base, registers);
> > +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP)
> > +		rkisp1_debug_dump_regs(rsz->rkisp1, m, rsz->regs_base,
> > +				       crop_registers);
> > +
> > +	return 0;
> >  }
> >  DEFINE_SHOW_ATTRIBUTE(rkisp1_debug_dump_rsz_regs);
> >  
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > index a4496ee2e9b4..5abe33f5fed4 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-dev.c
> > @@ -465,7 +465,8 @@ static const struct rkisp1_info px30_isp_info = {
> >  	.isrs = px30_isp_isrs,
> >  	.isr_size = ARRAY_SIZE(px30_isp_isrs),
> >  	.isp_ver = RKISP1_V12,
> > -	.features = RKISP1_FEATURE_MIPI_CSI2,
> > +	.features = RKISP1_FEATURE_MIPI_CSI2
> > +		  | RKISP1_FEATURE_DUAL_CROP,
> >  };
> >  
> >  static const char * const rk3399_isp_clks[] = {
> > @@ -484,7 +485,8 @@ static const struct rkisp1_info rk3399_isp_info = {
> >  	.isrs = rk3399_isp_isrs,
> >  	.isr_size = ARRAY_SIZE(rk3399_isp_isrs),
> >  	.isp_ver = RKISP1_V10,
> > -	.features = RKISP1_FEATURE_MIPI_CSI2,
> > +	.features = RKISP1_FEATURE_MIPI_CSI2
> > +		  | RKISP1_FEATURE_DUAL_CROP,
> >  };
> >  
> >  static const char * const imx8mp_isp_clks[] = {
> > @@ -503,6 +505,7 @@ static const struct rkisp1_info imx8mp_isp_info = {
> >  	.isrs = imx8mp_isp_isrs,
> >  	.isr_size = ARRAY_SIZE(imx8mp_isp_isrs),
> >  	.isp_ver = IMX8MP_V10,
> > +	.features = RKISP1_FEATURE_RSZ_CROP,
> >  };
> >  
> >  static const struct of_device_id rkisp1_of_match[] = {
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > index dd3e6c38be67..1fc54ab22b6d 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > @@ -168,6 +168,9 @@
> >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> >  
> > +/* RSZ_CROP_[XY]_DIR */
> > +#define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > +
> >  /* MI_IMSC - MI_MIS - MI_RIS - MI_ICR - MI_ISR */
> >  #define RKISP1_CIF_MI_FRAME(stream)			BIT((stream)->id)
> >  #define RKISP1_CIF_MI_MBLK_LINE				BIT(2)
> > @@ -926,6 +929,12 @@
> >  #define RKISP1_CIF_RSZ_PHASE_HC_SHD		0x004C
> >  #define RKISP1_CIF_RSZ_PHASE_VY_SHD		0x0050
> >  #define RKISP1_CIF_RSZ_PHASE_VC_SHD		0x0054
> > +#define RKISP1_CIF_RSZ_CROP_X_DIR		0x0058
> > +#define RKISP1_CIF_RSZ_CROP_Y_DIR		0x005C
> > +#define RKISP1_CIF_RSZ_CROP_X_DIR_SHD		0x0060
> > +#define RKISP1_CIF_RSZ_CROP_Y_DIR_SHD		0x0064
> > +#define RKISP1_CIF_RSZ_FRAME_RATE		0x0068
> > +#define RKISP1_CIF_RSZ_FORMAT_CONV_CTRL		0x006C
> >  
> >  #define RKISP1_CIF_MI_BASE			0x00001400
> >  #define RKISP1_CIF_MI_CTRL			(RKISP1_CIF_MI_BASE + 0x00000000)
> > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > index f4caa8f684aa..08bf3aa8088f 100644
> > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > @@ -244,6 +244,7 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
> >  {
> >  	u32 ratio, rsz_ctrl = 0;
> >  	unsigned int i;
> > +	u32 val;
> >  
> >  	/* No phase offset */
> >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_PHASE_HY, 0);
> > @@ -292,6 +293,18 @@ static void rkisp1_rsz_config_regs(struct rkisp1_resizer *rsz,
> >  
> >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, rsz_ctrl);
> >  
> > +	if (rsz->rkisp1->info->features & RKISP1_FEATURE_RSZ_CROP) {
> > +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->left, src_y->left + src_y->width - 1);
> > +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_X_DIR, val);
> > +		val = RKISP1_CIF_RSZ_CROP_XY_DIR(src_y->top, src_y->top + src_y->height - 1);
> > +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CROP_Y_DIR, val);
> > +
> > +		val = RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_INPUT_FORMAT_YCBCR_422
> > +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_OUTPUT_FORMAT_YCBCR_420
> > +		    | RKISP1_CIF_RSZ_FORMAT_CONV_CTRL_RSZ_PACK_FORMAT_SEMI_PLANAR;
> 
> Shouldn't this depend on the input and output formats of the resizer ?

Oops, yeah it should.


Paul

> 
> > +		rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_FORMAT_CONV_CTRL, val);
> > +	}
> > +
> >  	rkisp1_rsz_update_shadow(rsz, when);
> >  }
> >  
> > @@ -656,7 +669,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
> >  	enum rkisp1_shadow_regs_when when = RKISP1_SHADOW_REGS_SYNC;
> >  
> >  	if (!enable) {
> > -		rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> > +		if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> > +			rkisp1_dcrop_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> >  		rkisp1_rsz_disable(rsz, RKISP1_SHADOW_REGS_ASYNC);
> >  		return 0;
> >  	}
> > @@ -666,7 +680,8 @@ static int rkisp1_rsz_s_stream(struct v4l2_subdev *sd, int enable)
> >  
> >  	mutex_lock(&rsz->ops_lock);
> >  	rkisp1_rsz_config(rsz, when);
> > -	rkisp1_dcrop_config(rsz);
> > +	if (rkisp1->info->features & RKISP1_FEATURE_DUAL_CROP)
> > +		rkisp1_dcrop_config(rsz);
> >  
> >  	mutex_unlock(&rsz->ops_lock);
> >  	return 0;

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
  2022-06-17 23:03       ` Laurent Pinchart
@ 2022-07-04 10:40         ` paul.elder
  -1 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04 10:40 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Alexander Stein, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Laurent,

On Sat, Jun 18, 2022 at 02:03:17AM +0300, Laurent Pinchart wrote:
> Hi Alexander,
> 
> On Thu, Jun 16, 2022 at 10:05:06AM +0200, Alexander Stein wrote:
> > Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> > > The ISP that is integrated in the i.MX8MP uses different bits in the
> > > MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> > > compared to the on in the RK3399. In addition, it adds a new bit for
> > > enabling crop. Add new definitions for these bits for i.MX8MP devices,
> > > and update where they are set.
> > > 
> > > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > > ---
> > >  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
> > >  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
> > >  2 files changed, 12 insertions(+), 2 deletions(-)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> > > 34f4fe09c88d..24ad2ccec2a3 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > @@ -168,6 +168,10 @@
> > >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> > >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> > > 
> > > +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> > > +
> > 
> > Does it make sense to move this kind of information into struct rkisp1_info? 
> > This way you can skip the if (isp_ver == ...) thing.
> 
> Good question. Paul, what do you think ? If it doesn't get moved to the
> structure, I think I'd condition it by the RKISP1_FEATURE_RSZ_CROP
> feature bit instead of a version check, as it seems closely related. I'm
> actually leaning towards the latter.

Yeah I think the latter too.


Paul

> 
> > >  /* RSZ_CROP_[XY]_DIR */
> > >  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> > > 08bf3aa8088f..29a31b18a082 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> > > rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> > > RKISP1_CIF_RSZ_CTRL);
> > > 
> > >  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > >  	else
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > 
> > >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
> > >  }

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: (EXT) [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP
@ 2022-07-04 10:40         ` paul.elder
  0 siblings, 0 replies; 298+ messages in thread
From: paul.elder @ 2022-07-04 10:40 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Alexander Stein, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Laurent,

On Sat, Jun 18, 2022 at 02:03:17AM +0300, Laurent Pinchart wrote:
> Hi Alexander,
> 
> On Thu, Jun 16, 2022 at 10:05:06AM +0200, Alexander Stein wrote:
> > Am Dienstag, 14. Juni 2022, 21:11:27 CEST schrieb Paul Elder:
> > > The ISP that is integrated in the i.MX8MP uses different bits in the
> > > MRSZ_CTRL and SRSZ_CTRL registers for updating the configuration
> > > compared to the on in the RK3399. In addition, it adds a new bit for
> > > enabling crop. Add new definitions for these bits for i.MX8MP devices,
> > > and update where they are set.
> > > 
> > > Signed-off-by: Paul Elder <paul.elder@ideasonboard.com>
> > > ---
> > >  drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h   |  4 ++++
> > >  .../media/platform/rockchip/rkisp1/rkisp1-resizer.c    | 10 ++++++++--
> > >  2 files changed, 12 insertions(+), 2 deletions(-)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h index
> > > 34f4fe09c88d..24ad2ccec2a3 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-regs.h
> > > @@ -168,6 +168,10 @@
> > >  #define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO		BIT(9)
> > >  #define RKISP1_CIF_RSZ_SCALER_FACTOR			BIT(16)
> > > 
> > > +#define RKISP1_CIF_RSZ_CTRL_CROP_ENABLE_IMX		BIT(8)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX			BIT(9)
> > > +#define RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX		BIT(10)
> > > +
> > 
> > Does it make sense to move this kind of information into struct rkisp1_info? 
> > This way you can skip the if (isp_ver == ...) thing.
> 
> Good question. Paul, what do you think ? If it doesn't get moved to the
> structure, I think I'd condition it by the RKISP1_FEATURE_RSZ_CROP
> feature bit instead of a version check, as it seems closely related. I'm
> actually leaning towards the latter.

Yeah I think the latter too.


Paul

> 
> > >  /* RSZ_CROP_[XY]_DIR */
> > >  #define RKISP1_CIF_RSZ_CROP_XY_DIR(start, end)		((end) << 16 | (start) << 0)
> > > 
> > > diff --git a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c index
> > > 08bf3aa8088f..29a31b18a082 100644
> > > --- a/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > +++ b/drivers/media/platform/rockchip/rkisp1/rkisp1-resizer.c
> > > @@ -209,9 +209,15 @@ static void rkisp1_rsz_update_shadow(struct
> > > rkisp1_resizer *rsz, u32 ctrl_cfg = rkisp1_rsz_read(rsz,
> > > RKISP1_CIF_RSZ_CTRL);
> > > 
> > >  	if (when == RKISP1_SHADOW_REGS_ASYNC)
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_AUTO;
> > >  	else
> > > -		ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > +		if (rsz->rkisp1->info->isp_ver == IMX8MP_V10)
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD_IMX;
> > > +		else
> > > +			ctrl_cfg |= RKISP1_CIF_RSZ_CTRL_CFG_UPD;
> > > 
> > >  	rkisp1_rsz_write(rsz, RKISP1_CIF_RSZ_CTRL, ctrl_cfg);
> > >  }

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-06-25 17:00       ` Laurent Pinchart
@ 2022-07-07  6:52         ` Hans Verkuil
  -1 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-07-07  6:52 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip



On 6/25/22 19:00, Laurent Pinchart wrote:
> Hi Hans,
> 
> On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
>> On 6/14/22 21:11, Paul Elder wrote:
>>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>>
>>> The media_entity_remote_pad() helper function returns the first remote
>>> pad it find connected to a given pad. Beside being possibly ill-named
>>> (as it operates on a pad, not an entity) and non-deterministic (as it
>>> stops at the first enabled link), the fact that it returns the first
>>> match makes it unsuitable for drivers that need to guarantee that a
>>> single link is enabled, for instance when an entity can process data
>>> from one of multiple sources at a time.
>>
>> Question: of all the callers of this function, are there any that really
>> need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
>>
>> Would it be possible to replace all callers of the old function with the
>> new function? If that's the case, then the _unique suffix can be dropped,
>> since that would effectively be the default. And if a function is needed
>> to handle the case where there are multiple enabled links, then a new
>> function should be created.
> 
> I don't think so. media_entity_remote_pad() operates on a pad, switching
> to media_pad_remote_pad_unique() wouldn't work on subdevs that have
> multiple sink or source pads with one active link each.

Do we have those today in the mainline kernel? Just checking...

Regards,

	Hans

> 
>> Also, media_entity_remote_pad() should really be renamed to
>> media_pad_remote_pad_first() or something like that, right? I'm not saying
>> you should, but that's really what it does, as I understand it.
> 
> Yes, I think that would make sense, and it would freethe
> media_entity_remote_pad() name, so the new function wouldn't need the
> _unique suffix. I'll give it a try.
> 
>>> For those use cases, add a new helper function,
>>> media_entity_remote_pad_unique(), that operates on an entity and returns
>>> a remote pad, with a guarantee that only one link is enabled. To ease
>>> its use in drivers, also add an inline wrapper that locates source pads
>>> specifically. A wrapper that locates sink pads can easily be added when
>>> needed.
>>>
>>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>> ---
>>>  Documentation/driver-api/media/mc-core.rst |  4 +-
>>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>>>  3 files changed, 85 insertions(+), 2 deletions(-)
>>>
>>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
>>> index 02481a2513b9..a2d1e32e3abb 100644
>>> --- a/Documentation/driver-api/media/mc-core.rst
>>> +++ b/Documentation/driver-api/media/mc-core.rst
>>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>>>  
>>>  Helper functions can be used to find a link between two given pads, or a pad
>>>  connected to another pad through an enabled link
>>> -:c:func:`media_entity_find_link()` and
>>> -:c:func:`media_entity_remote_pad()`.
>>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
>>> +:c:func:`media_entity_remote_source_pad()`).
>>>  
>>>  Use count and power handling
>>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
>>> index 11f5207f73aa..1febf5a86be6 100644
>>> --- a/drivers/media/mc/mc-entity.c
>>> +++ b/drivers/media/mc/mc-entity.c
>>> @@ -9,6 +9,7 @@
>>>   */
>>>  
>>>  #include <linux/bitmap.h>
>>> +#include <linux/list.h>
>>>  #include <linux/property.h>
>>>  #include <linux/slab.h>
>>>  #include <media/media-entity.h>
>>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>>>  }
>>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>>>  
>>> +struct media_pad *
>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>> +			       unsigned int type)
>>> +{
>>> +	struct media_pad *pad = NULL;
>>> +	struct media_link *link;
>>> +
>>> +	list_for_each_entry(link, &entity->links, list) {
>>> +		struct media_pad *local_pad;
>>> +		struct media_pad *remote_pad;
>>> +
>>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
>>> +			continue;
>>> +
>>> +		if (type == MEDIA_PAD_FL_SOURCE) {
>>> +			local_pad = link->sink;
>>> +			remote_pad = link->source;
>>> +		} else {
>>> +			local_pad = link->source;
>>> +			remote_pad = link->sink;
>>> +		}
>>> +
>>> +		if (local_pad->entity == entity) {
>>> +			if (pad)
>>> +				return ERR_PTR(-ENOTUNIQ);
>>> +
>>> +			pad = remote_pad;
>>> +		}
>>> +	}
>>> +
>>> +	if (!pad)
>>> +		return ERR_PTR(-ENOLINK);
>>> +
>>> +	return pad;
>>> +}
>>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>>> +
>>>  static void media_interface_init(struct media_device *mdev,
>>>  				 struct media_interface *intf,
>>>  				 u32 gobj_type,
>>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
>>> index a9a1c0ec5d1c..33d5f52719a0 100644
>>> --- a/include/media/media-entity.h
>>> +++ b/include/media/media-entity.h
>>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>>>   */
>>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>>>  
>>> +/**
>>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
>>> + * @entity: The entity
>>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
>>> + *
>>> + * Search for and return a remote pad of @type connected to @entity through an
>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>> + * is returned.
>>> + *
>>> + * The uniqueness constraint makes this helper function suitable for entities
>>> + * that support a single active source or sink at a time.
>>> + *
>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>> + * if an error occurs:
>>> + *
>>> + * * -ENOTUNIQ - Multiple links are enabled
>>> + * * -ENOLINK - No connected pad found
>>> + */
>>> +struct media_pad *
>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>> +			       unsigned int type);
>>> +
>>> +/**
>>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
>>> + * @entity: The entity
>>> + *
>>> + * Search for and return a remote source pad connected to @entity through an
>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>> + * is returned.
>>> + *
>>> + * The uniqueness constraint makes this helper function suitable for entities
>>> + * that support a single active source at a time.
>>> + *
>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>> + * if an error occurs:
>>> + *
>>> + * * -ENOTUNIQ - Multiple links are enabled
>>> + * * -ENOLINK - No connected pad found
>>> + */
>>> +static inline struct media_pad *
>>> +media_entity_remote_source_pad(const struct media_entity *entity)
>>> +{
>>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>>> +}
>>> +
>>>  /**
>>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>>>   * @entity: The entity
> 

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-07-07  6:52         ` Hans Verkuil
  0 siblings, 0 replies; 298+ messages in thread
From: Hans Verkuil @ 2022-07-07  6:52 UTC (permalink / raw)
  To: Laurent Pinchart
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip



On 6/25/22 19:00, Laurent Pinchart wrote:
> Hi Hans,
> 
> On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
>> On 6/14/22 21:11, Paul Elder wrote:
>>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>>
>>> The media_entity_remote_pad() helper function returns the first remote
>>> pad it find connected to a given pad. Beside being possibly ill-named
>>> (as it operates on a pad, not an entity) and non-deterministic (as it
>>> stops at the first enabled link), the fact that it returns the first
>>> match makes it unsuitable for drivers that need to guarantee that a
>>> single link is enabled, for instance when an entity can process data
>>> from one of multiple sources at a time.
>>
>> Question: of all the callers of this function, are there any that really
>> need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
>>
>> Would it be possible to replace all callers of the old function with the
>> new function? If that's the case, then the _unique suffix can be dropped,
>> since that would effectively be the default. And if a function is needed
>> to handle the case where there are multiple enabled links, then a new
>> function should be created.
> 
> I don't think so. media_entity_remote_pad() operates on a pad, switching
> to media_pad_remote_pad_unique() wouldn't work on subdevs that have
> multiple sink or source pads with one active link each.

Do we have those today in the mainline kernel? Just checking...

Regards,

	Hans

> 
>> Also, media_entity_remote_pad() should really be renamed to
>> media_pad_remote_pad_first() or something like that, right? I'm not saying
>> you should, but that's really what it does, as I understand it.
> 
> Yes, I think that would make sense, and it would freethe
> media_entity_remote_pad() name, so the new function wouldn't need the
> _unique suffix. I'll give it a try.
> 
>>> For those use cases, add a new helper function,
>>> media_entity_remote_pad_unique(), that operates on an entity and returns
>>> a remote pad, with a guarantee that only one link is enabled. To ease
>>> its use in drivers, also add an inline wrapper that locates source pads
>>> specifically. A wrapper that locates sink pads can easily be added when
>>> needed.
>>>
>>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
>>> ---
>>>  Documentation/driver-api/media/mc-core.rst |  4 +-
>>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
>>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
>>>  3 files changed, 85 insertions(+), 2 deletions(-)
>>>
>>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
>>> index 02481a2513b9..a2d1e32e3abb 100644
>>> --- a/Documentation/driver-api/media/mc-core.rst
>>> +++ b/Documentation/driver-api/media/mc-core.rst
>>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
>>>  
>>>  Helper functions can be used to find a link between two given pads, or a pad
>>>  connected to another pad through an enabled link
>>> -:c:func:`media_entity_find_link()` and
>>> -:c:func:`media_entity_remote_pad()`.
>>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
>>> +:c:func:`media_entity_remote_source_pad()`).
>>>  
>>>  Use count and power handling
>>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
>>> index 11f5207f73aa..1febf5a86be6 100644
>>> --- a/drivers/media/mc/mc-entity.c
>>> +++ b/drivers/media/mc/mc-entity.c
>>> @@ -9,6 +9,7 @@
>>>   */
>>>  
>>>  #include <linux/bitmap.h>
>>> +#include <linux/list.h>
>>>  #include <linux/property.h>
>>>  #include <linux/slab.h>
>>>  #include <media/media-entity.h>
>>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
>>>  }
>>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
>>>  
>>> +struct media_pad *
>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>> +			       unsigned int type)
>>> +{
>>> +	struct media_pad *pad = NULL;
>>> +	struct media_link *link;
>>> +
>>> +	list_for_each_entry(link, &entity->links, list) {
>>> +		struct media_pad *local_pad;
>>> +		struct media_pad *remote_pad;
>>> +
>>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
>>> +			continue;
>>> +
>>> +		if (type == MEDIA_PAD_FL_SOURCE) {
>>> +			local_pad = link->sink;
>>> +			remote_pad = link->source;
>>> +		} else {
>>> +			local_pad = link->source;
>>> +			remote_pad = link->sink;
>>> +		}
>>> +
>>> +		if (local_pad->entity == entity) {
>>> +			if (pad)
>>> +				return ERR_PTR(-ENOTUNIQ);
>>> +
>>> +			pad = remote_pad;
>>> +		}
>>> +	}
>>> +
>>> +	if (!pad)
>>> +		return ERR_PTR(-ENOLINK);
>>> +
>>> +	return pad;
>>> +}
>>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
>>> +
>>>  static void media_interface_init(struct media_device *mdev,
>>>  				 struct media_interface *intf,
>>>  				 u32 gobj_type,
>>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
>>> index a9a1c0ec5d1c..33d5f52719a0 100644
>>> --- a/include/media/media-entity.h
>>> +++ b/include/media/media-entity.h
>>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
>>>   */
>>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
>>>  
>>> +/**
>>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
>>> + * @entity: The entity
>>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
>>> + *
>>> + * Search for and return a remote pad of @type connected to @entity through an
>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>> + * is returned.
>>> + *
>>> + * The uniqueness constraint makes this helper function suitable for entities
>>> + * that support a single active source or sink at a time.
>>> + *
>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>> + * if an error occurs:
>>> + *
>>> + * * -ENOTUNIQ - Multiple links are enabled
>>> + * * -ENOLINK - No connected pad found
>>> + */
>>> +struct media_pad *
>>> +media_entity_remote_pad_unique(const struct media_entity *entity,
>>> +			       unsigned int type);
>>> +
>>> +/**
>>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
>>> + * @entity: The entity
>>> + *
>>> + * Search for and return a remote source pad connected to @entity through an
>>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
>>> + * is returned.
>>> + *
>>> + * The uniqueness constraint makes this helper function suitable for entities
>>> + * that support a single active source at a time.
>>> + *
>>> + * Return: A pointer to the remote pad, or one of the following error pointers
>>> + * if an error occurs:
>>> + *
>>> + * * -ENOTUNIQ - Multiple links are enabled
>>> + * * -ENOLINK - No connected pad found
>>> + */
>>> +static inline struct media_pad *
>>> +media_entity_remote_source_pad(const struct media_entity *entity)
>>> +{
>>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
>>> +}
>>> +
>>>  /**
>>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
>>>   * @entity: The entity
> 

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
  2022-07-07  6:52         ` Hans Verkuil
@ 2022-07-07 11:50           ` Laurent Pinchart
  -1 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-07 11:50 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Thu, Jul 07, 2022 at 08:52:16AM +0200, Hans Verkuil wrote:
> On 6/25/22 19:00, Laurent Pinchart wrote:
> > On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
> >> On 6/14/22 21:11, Paul Elder wrote:
> >>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>>
> >>> The media_entity_remote_pad() helper function returns the first remote
> >>> pad it find connected to a given pad. Beside being possibly ill-named
> >>> (as it operates on a pad, not an entity) and non-deterministic (as it
> >>> stops at the first enabled link), the fact that it returns the first
> >>> match makes it unsuitable for drivers that need to guarantee that a
> >>> single link is enabled, for instance when an entity can process data
> >>> from one of multiple sources at a time.
> >>
> >> Question: of all the callers of this function, are there any that really
> >> need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
> >>
> >> Would it be possible to replace all callers of the old function with the
> >> new function? If that's the case, then the _unique suffix can be dropped,
> >> since that would effectively be the default. And if a function is needed
> >> to handle the case where there are multiple enabled links, then a new
> >> function should be created.
> > 
> > I don't think so. media_entity_remote_pad() operates on a pad, switching
> > to media_pad_remote_pad_unique() wouldn't work on subdevs that have
> > multiple sink or source pads with one active link each.
> 
> Do we have those today in the mainline kernel? Just checking...

Re-reading my reply, it seems I may have been mistaken. We may be able
to ditch media_pad_remote_pad_first() and replace it with
media_pad_remote_pad_unique() (at least in the majority of cases), but
we'll need to carefully review each user.

> >> Also, media_entity_remote_pad() should really be renamed to
> >> media_pad_remote_pad_first() or something like that, right? I'm not saying
> >> you should, but that's really what it does, as I understand it.
> > 
> > Yes, I think that would make sense, and it would freethe
> > media_entity_remote_pad() name, so the new function wouldn't need the
> > _unique suffix. I'll give it a try.
> > 
> >>> For those use cases, add a new helper function,
> >>> media_entity_remote_pad_unique(), that operates on an entity and returns
> >>> a remote pad, with a guarantee that only one link is enabled. To ease
> >>> its use in drivers, also add an inline wrapper that locates source pads
> >>> specifically. A wrapper that locates sink pads can easily be added when
> >>> needed.
> >>>
> >>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>> ---
> >>>  Documentation/driver-api/media/mc-core.rst |  4 +-
> >>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >>>  3 files changed, 85 insertions(+), 2 deletions(-)
> >>>
> >>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> >>> index 02481a2513b9..a2d1e32e3abb 100644
> >>> --- a/Documentation/driver-api/media/mc-core.rst
> >>> +++ b/Documentation/driver-api/media/mc-core.rst
> >>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >>>  
> >>>  Helper functions can be used to find a link between two given pads, or a pad
> >>>  connected to another pad through an enabled link
> >>> -:c:func:`media_entity_find_link()` and
> >>> -:c:func:`media_entity_remote_pad()`.
> >>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> >>> +:c:func:`media_entity_remote_source_pad()`).
> >>>  
> >>>  Use count and power handling
> >>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> >>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> >>> index 11f5207f73aa..1febf5a86be6 100644
> >>> --- a/drivers/media/mc/mc-entity.c
> >>> +++ b/drivers/media/mc/mc-entity.c
> >>> @@ -9,6 +9,7 @@
> >>>   */
> >>>  
> >>>  #include <linux/bitmap.h>
> >>> +#include <linux/list.h>
> >>>  #include <linux/property.h>
> >>>  #include <linux/slab.h>
> >>>  #include <media/media-entity.h>
> >>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >>>  }
> >>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >>>  
> >>> +struct media_pad *
> >>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>> +			       unsigned int type)
> >>> +{
> >>> +	struct media_pad *pad = NULL;
> >>> +	struct media_link *link;
> >>> +
> >>> +	list_for_each_entry(link, &entity->links, list) {
> >>> +		struct media_pad *local_pad;
> >>> +		struct media_pad *remote_pad;
> >>> +
> >>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> >>> +			continue;
> >>> +
> >>> +		if (type == MEDIA_PAD_FL_SOURCE) {
> >>> +			local_pad = link->sink;
> >>> +			remote_pad = link->source;
> >>> +		} else {
> >>> +			local_pad = link->source;
> >>> +			remote_pad = link->sink;
> >>> +		}
> >>> +
> >>> +		if (local_pad->entity == entity) {
> >>> +			if (pad)
> >>> +				return ERR_PTR(-ENOTUNIQ);
> >>> +
> >>> +			pad = remote_pad;
> >>> +		}
> >>> +	}
> >>> +
> >>> +	if (!pad)
> >>> +		return ERR_PTR(-ENOLINK);
> >>> +
> >>> +	return pad;
> >>> +}
> >>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >>> +
> >>>  static void media_interface_init(struct media_device *mdev,
> >>>  				 struct media_interface *intf,
> >>>  				 u32 gobj_type,
> >>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> >>> index a9a1c0ec5d1c..33d5f52719a0 100644
> >>> --- a/include/media/media-entity.h
> >>> +++ b/include/media/media-entity.h
> >>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >>>   */
> >>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >>>  
> >>> +/**
> >>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> >>> + * @entity: The entity
> >>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> >>> + *
> >>> + * Search for and return a remote pad of @type connected to @entity through an
> >>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>> + * is returned.
> >>> + *
> >>> + * The uniqueness constraint makes this helper function suitable for entities
> >>> + * that support a single active source or sink at a time.
> >>> + *
> >>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>> + * if an error occurs:
> >>> + *
> >>> + * * -ENOTUNIQ - Multiple links are enabled
> >>> + * * -ENOLINK - No connected pad found
> >>> + */
> >>> +struct media_pad *
> >>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>> +			       unsigned int type);
> >>> +
> >>> +/**
> >>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> >>> + * @entity: The entity
> >>> + *
> >>> + * Search for and return a remote source pad connected to @entity through an
> >>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>> + * is returned.
> >>> + *
> >>> + * The uniqueness constraint makes this helper function suitable for entities
> >>> + * that support a single active source at a time.
> >>> + *
> >>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>> + * if an error occurs:
> >>> + *
> >>> + * * -ENOTUNIQ - Multiple links are enabled
> >>> + * * -ENOLINK - No connected pad found
> >>> + */
> >>> +static inline struct media_pad *
> >>> +media_entity_remote_source_pad(const struct media_entity *entity)
> >>> +{
> >>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >>> +}
> >>> +
> >>>  /**
> >>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >>>   * @entity: The entity

-- 
Regards,

Laurent Pinchart

^ permalink raw reply	[flat|nested] 298+ messages in thread

* Re: [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad
@ 2022-07-07 11:50           ` Laurent Pinchart
  0 siblings, 0 replies; 298+ messages in thread
From: Laurent Pinchart @ 2022-07-07 11:50 UTC (permalink / raw)
  To: Hans Verkuil
  Cc: Paul Elder, linux-media, dafna, heiko, jeanmichel.hautbois,
	jacopo, djrscally, helen.koike, linux-rockchip

Hi Hans,

On Thu, Jul 07, 2022 at 08:52:16AM +0200, Hans Verkuil wrote:
> On 6/25/22 19:00, Laurent Pinchart wrote:
> > On Fri, Jun 17, 2022 at 01:48:05PM +0200, Hans Verkuil wrote:
> >> On 6/14/22 21:11, Paul Elder wrote:
> >>> From: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>>
> >>> The media_entity_remote_pad() helper function returns the first remote
> >>> pad it find connected to a given pad. Beside being possibly ill-named
> >>> (as it operates on a pad, not an entity) and non-deterministic (as it
> >>> stops at the first enabled link), the fact that it returns the first
> >>> match makes it unsuitable for drivers that need to guarantee that a
> >>> single link is enabled, for instance when an entity can process data
> >>> from one of multiple sources at a time.
> >>
> >> Question: of all the callers of this function, are there any that really
> >> need media_entity_remote_pad() instead of media_pad_remote_pad_unique()?
> >>
> >> Would it be possible to replace all callers of the old function with the
> >> new function? If that's the case, then the _unique suffix can be dropped,
> >> since that would effectively be the default. And if a function is needed
> >> to handle the case where there are multiple enabled links, then a new
> >> function should be created.
> > 
> > I don't think so. media_entity_remote_pad() operates on a pad, switching
> > to media_pad_remote_pad_unique() wouldn't work on subdevs that have
> > multiple sink or source pads with one active link each.
> 
> Do we have those today in the mainline kernel? Just checking...

Re-reading my reply, it seems I may have been mistaken. We may be able
to ditch media_pad_remote_pad_first() and replace it with
media_pad_remote_pad_unique() (at least in the majority of cases), but
we'll need to carefully review each user.

> >> Also, media_entity_remote_pad() should really be renamed to
> >> media_pad_remote_pad_first() or something like that, right? I'm not saying
> >> you should, but that's really what it does, as I understand it.
> > 
> > Yes, I think that would make sense, and it would freethe
> > media_entity_remote_pad() name, so the new function wouldn't need the
> > _unique suffix. I'll give it a try.
> > 
> >>> For those use cases, add a new helper function,
> >>> media_entity_remote_pad_unique(), that operates on an entity and returns
> >>> a remote pad, with a guarantee that only one link is enabled. To ease
> >>> its use in drivers, also add an inline wrapper that locates source pads
> >>> specifically. A wrapper that locates sink pads can easily be added when
> >>> needed.
> >>>
> >>> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
> >>> ---
> >>>  Documentation/driver-api/media/mc-core.rst |  4 +-
> >>>  drivers/media/mc/mc-entity.c               | 38 ++++++++++++++++++
> >>>  include/media/media-entity.h               | 45 ++++++++++++++++++++++
> >>>  3 files changed, 85 insertions(+), 2 deletions(-)
> >>>
> >>> diff --git a/Documentation/driver-api/media/mc-core.rst b/Documentation/driver-api/media/mc-core.rst
> >>> index 02481a2513b9..a2d1e32e3abb 100644
> >>> --- a/Documentation/driver-api/media/mc-core.rst
> >>> +++ b/Documentation/driver-api/media/mc-core.rst
> >>> @@ -186,8 +186,8 @@ is required and the graph structure can be freed normally.
> >>>  
> >>>  Helper functions can be used to find a link between two given pads, or a pad
> >>>  connected to another pad through an enabled link
> >>> -:c:func:`media_entity_find_link()` and
> >>> -:c:func:`media_entity_remote_pad()`.
> >>> +(:c:func:`media_entity_find_link()`, :c:func:`media_entity_remote_pad()` and
> >>> +:c:func:`media_entity_remote_source_pad()`).
> >>>  
> >>>  Use count and power handling
> >>>  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
> >>> diff --git a/drivers/media/mc/mc-entity.c b/drivers/media/mc/mc-entity.c
> >>> index 11f5207f73aa..1febf5a86be6 100644
> >>> --- a/drivers/media/mc/mc-entity.c
> >>> +++ b/drivers/media/mc/mc-entity.c
> >>> @@ -9,6 +9,7 @@
> >>>   */
> >>>  
> >>>  #include <linux/bitmap.h>
> >>> +#include <linux/list.h>
> >>>  #include <linux/property.h>
> >>>  #include <linux/slab.h>
> >>>  #include <media/media-entity.h>
> >>> @@ -920,6 +921,43 @@ struct media_pad *media_entity_remote_pad(const struct media_pad *pad)
> >>>  }
> >>>  EXPORT_SYMBOL_GPL(media_entity_remote_pad);
> >>>  
> >>> +struct media_pad *
> >>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>> +			       unsigned int type)
> >>> +{
> >>> +	struct media_pad *pad = NULL;
> >>> +	struct media_link *link;
> >>> +
> >>> +	list_for_each_entry(link, &entity->links, list) {
> >>> +		struct media_pad *local_pad;
> >>> +		struct media_pad *remote_pad;
> >>> +
> >>> +		if (!(link->flags & MEDIA_LNK_FL_ENABLED))
> >>> +			continue;
> >>> +
> >>> +		if (type == MEDIA_PAD_FL_SOURCE) {
> >>> +			local_pad = link->sink;
> >>> +			remote_pad = link->source;
> >>> +		} else {
> >>> +			local_pad = link->source;
> >>> +			remote_pad = link->sink;
> >>> +		}
> >>> +
> >>> +		if (local_pad->entity == entity) {
> >>> +			if (pad)
> >>> +				return ERR_PTR(-ENOTUNIQ);
> >>> +
> >>> +			pad = remote_pad;
> >>> +		}
> >>> +	}
> >>> +
> >>> +	if (!pad)
> >>> +		return ERR_PTR(-ENOLINK);
> >>> +
> >>> +	return pad;
> >>> +}
> >>> +EXPORT_SYMBOL_GPL(media_entity_remote_pad_unique);
> >>> +
> >>>  static void media_interface_init(struct media_device *mdev,
> >>>  				 struct media_interface *intf,
> >>>  				 u32 gobj_type,
> >>> diff --git a/include/media/media-entity.h b/include/media/media-entity.h
> >>> index a9a1c0ec5d1c..33d5f52719a0 100644
> >>> --- a/include/media/media-entity.h
> >>> +++ b/include/media/media-entity.h
> >>> @@ -859,6 +859,51 @@ struct media_link *media_entity_find_link(struct media_pad *source,
> >>>   */
> >>>  struct media_pad *media_entity_remote_pad(const struct media_pad *pad);
> >>>  
> >>> +/**
> >>> + * media_entity_remote_pad_unique - Find a remote pad connected to an entity
> >>> + * @entity: The entity
> >>> + * @type: The type of pad to find (MEDIA_PAD_FL_SINK or MEDIA_PAD_FL_SOURCE)
> >>> + *
> >>> + * Search for and return a remote pad of @type connected to @entity through an
> >>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>> + * is returned.
> >>> + *
> >>> + * The uniqueness constraint makes this helper function suitable for entities
> >>> + * that support a single active source or sink at a time.
> >>> + *
> >>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>> + * if an error occurs:
> >>> + *
> >>> + * * -ENOTUNIQ - Multiple links are enabled
> >>> + * * -ENOLINK - No connected pad found
> >>> + */
> >>> +struct media_pad *
> >>> +media_entity_remote_pad_unique(const struct media_entity *entity,
> >>> +			       unsigned int type);
> >>> +
> >>> +/**
> >>> + * media_entity_remote_source_pad - Find a remote source pad connected to an entity
> >>> + * @entity: The entity
> >>> + *
> >>> + * Search for and return a remote source pad connected to @entity through an
> >>> + * enabled link. If multiple (or no) remote pads match these criteria, an error
> >>> + * is returned.
> >>> + *
> >>> + * The uniqueness constraint makes this helper function suitable for entities
> >>> + * that support a single active source at a time.
> >>> + *
> >>> + * Return: A pointer to the remote pad, or one of the following error pointers
> >>> + * if an error occurs:
> >>> + *
> >>> + * * -ENOTUNIQ - Multiple links are enabled
> >>> + * * -ENOLINK - No connected pad found
> >>> + */
> >>> +static inline struct media_pad *
> >>> +media_entity_remote_source_pad(const struct media_entity *entity)
> >>> +{
> >>> +	return media_entity_remote_pad_unique(entity, MEDIA_PAD_FL_SOURCE);
> >>> +}
> >>> +
> >>>  /**
> >>>   * media_entity_is_streaming - Test if an entity is part of a streaming pipeline
> >>>   * @entity: The entity

-- 
Regards,

Laurent Pinchart

_______________________________________________
Linux-rockchip mailing list
Linux-rockchip@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-rockchip

^ permalink raw reply	[flat|nested] 298+ messages in thread

end of thread, other threads:[~2022-07-07 11:51 UTC | newest]

Thread overview: 298+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-06-14 19:10 [PATCH 00/55] media: rkisp1: Cleanups and add support for i.MX8MP Paul Elder
2022-06-14 19:10 ` Paul Elder
2022-06-14 19:10 ` [PATCH 01/55] media: rkisp1: debug: Add dump file in debugfs for MI buffer registers Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-15 22:41   ` Laurent Pinchart
2022-06-15 22:41     ` Laurent Pinchart
2022-06-25 17:59     ` Laurent Pinchart
2022-06-25 17:59       ` Laurent Pinchart
2022-07-04  3:46       ` paul.elder
2022-07-04  3:46         ` paul.elder
2022-06-14 19:10 ` [PATCH 02/55] media: rkisp1: Enable compilation on ARCH_MXC Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 14:17   ` Dafna Hirschfeld
2022-06-24 14:17     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 03/55] media: rkisp1: debug: Add debugfs files to monitor MI and ISP interrupts Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-16  0:44   ` Laurent Pinchart
2022-06-16  0:44     ` Laurent Pinchart
2022-07-04  3:47     ` paul.elder
2022-07-04  3:47       ` paul.elder
2022-06-14 19:10 ` [PATCH 04/55] media: rkisp1: Disable runtime PM in probe error path Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 14:21   ` Dafna Hirschfeld
2022-06-24 14:21     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 05/55] media: rkisp1: Read the ID register at probe time instead of streamon Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 14:26   ` Dafna Hirschfeld
2022-06-24 14:26     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 06/55] media: rkisp1: Rename rkisp1_match_data to rkisp1_info Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 14:29   ` Dafna Hirschfeld
2022-06-24 14:29     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 07/55] media: rkisp1: Save info pointer in rkisp1_device Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 14:34   ` Dafna Hirschfeld
2022-06-24 14:34     ` Dafna Hirschfeld
2022-06-24 14:47     ` Laurent Pinchart
2022-06-24 14:47       ` Laurent Pinchart
2022-06-30 21:28       ` Dafna Hirschfeld
2022-06-30 21:28         ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 08/55] media: rkisp1: Access ISP version from info pointer Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 14:35   ` Dafna Hirschfeld
2022-06-24 14:35     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 09/55] media: rkisp1: Make rkisp1_isp_mbus_info common Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-16  0:50   ` Laurent Pinchart
2022-06-16  0:50     ` Laurent Pinchart
2022-06-24 14:54   ` Dafna Hirschfeld
2022-06-24 14:54     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 10/55] media: rkisp1: cap: Print debug message on failed link validation Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-16  7:32   ` (EXT) " Alexander Stein
2022-06-16  7:32     ` Alexander Stein
2022-06-16  7:41     ` Laurent Pinchart
2022-06-16  7:41       ` Laurent Pinchart
2022-06-16  7:59       ` (EXT) " Alexander Stein
2022-06-16  7:59         ` Alexander Stein
2022-06-24 15:00   ` Dafna Hirschfeld
2022-06-24 15:00     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 11/55] media: rkisp1: Move sensor .s_stream() call to ISP Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 15:14   ` Dafna Hirschfeld
2022-06-24 15:14     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 12/55] media: rkisp1: Reject sensors without pixel rate control at bound time Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 18:20   ` Dafna Hirschfeld
2022-06-24 18:20     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 13/55] media: rkisp1: Create link from sensor to ISP at notifier " Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 18:40   ` Dafna Hirschfeld
2022-06-24 18:40     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 14/55] media: rkisp1: Create internal links at probe time Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 18:43   ` Dafna Hirschfeld
2022-06-24 18:43     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 15/55] media: rkisp1: Rename rkisp1_subdev_notifier() to rkisp1_subdev_notifier_register() Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-24 18:44   ` Dafna Hirschfeld
2022-06-24 18:44     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 16/55] media: v4l2-async: Add notifier operation to destroy asd instances Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-15 22:36   ` Laurent Pinchart
2022-06-15 22:36     ` Laurent Pinchart
2022-06-20 14:27   ` Hans Verkuil
2022-06-20 14:27     ` Hans Verkuil
2022-06-14 19:10 ` [PATCH 17/55] media: rkisp1: Fix sensor source pad retrieval at bound time Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-07-01  4:36   ` Dafna Hirschfeld
2022-07-01  4:36     ` Dafna Hirschfeld
2022-07-01 11:29     ` Laurent Pinchart
2022-07-01 11:29       ` Laurent Pinchart
2022-06-14 19:10 ` [PATCH 18/55] media: rkisp1: Split CSI handling to separate file Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  3:48   ` Dafna Hirschfeld
2022-06-25  3:48     ` Dafna Hirschfeld
2022-06-25 10:18     ` Laurent Pinchart
2022-06-25 10:18       ` Laurent Pinchart
2022-06-14 19:10 ` [PATCH 19/55] media: rkisp1: isp: Start CSI-2 receiver before ISP Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  3:51   ` Dafna Hirschfeld
2022-06-25  3:51     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 20/55] media: rkisp1: csi: Handle CSI-2 RX configuration fully in rkisp1-csi.c Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:00   ` Dafna Hirschfeld
2022-06-25  4:00     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 21/55] media: rkisp1: csi: Rename CSI functions with a common rkisp1_csi prefix Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:03   ` Dafna Hirschfeld
2022-06-25  4:03     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 22/55] media: rkisp1: csi: Move start delay to rkisp1_csi_start() Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:05   ` Dafna Hirschfeld
2022-06-25  4:05     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 23/55] media: rkisp1: csi: Pass sensor pointer to rkisp1_csi_config() Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:28   ` Dafna Hirschfeld
2022-06-25  4:28     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 24/55] media: rkisp1: csi: Constify argument to rkisp1_csi_start() Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:29   ` Dafna Hirschfeld
2022-06-25  4:29     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 25/55] media: rkisp1: isp: Don't initialize ret to 0 in rkisp1_isp_s_stream() Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:46   ` Dafna Hirschfeld
2022-06-25  4:46     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 26/55] media: rkisp1: isp: Pass mbus type and flags to rkisp1_config_cif() Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-25  4:32   ` Dafna Hirschfeld
2022-06-25  4:32     ` Dafna Hirschfeld
2022-06-14 19:10 ` [PATCH 27/55] media: rkisp1: isp: Rename rkisp1_device.active_sensor to source Paul Elder
2022-06-14 19:10   ` Paul Elder
2022-06-30 21:57   ` Dafna Hirschfeld
2022-06-30 21:57     ` Dafna Hirschfeld
2022-07-01  4:42   ` Dafna Hirschfeld
2022-07-01  4:42     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 28/55] media: rkisp1: isp: Add container_of wrapper to cast subdev to rkisp1_isp Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  4:48   ` Dafna Hirschfeld
2022-06-25  4:48     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 29/55] media: rkisp1: isp: Add rkisp1_device backpointer " Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  4:50   ` Dafna Hirschfeld
2022-06-25  4:50     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 30/55] media: rkisp1: isp: Pass rkisp1_isp pointer to internal ISP functions Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  4:52   ` Dafna Hirschfeld
2022-06-25  4:52     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 31/55] media: rkisp1: isp: Move input configuration to rkisp1_config_isp() Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  5:00   ` Dafna Hirschfeld
2022-06-25  5:00     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 32/55] media: rkisp1: isp: Merge ISP_ACQ_PROP configuration in single variable Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  5:03   ` Dafna Hirschfeld
2022-06-25  5:03     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 33/55] media: rkisp1: isp: Initialize some variables at declaration time Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  5:04   ` Dafna Hirschfeld
2022-06-25  5:04     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 34/55] media: rkisp1: isp: Fix whitespace issues Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  5:05   ` Dafna Hirschfeld
2022-06-25  5:05     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 35/55] media: rkisp1: isp: Constify various local variables Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  5:07   ` Dafna Hirschfeld
2022-06-25  5:07     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 36/55] media: rkisp1: isp: Rename rkisp1_get_remote_source() Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  5:09   ` Dafna Hirschfeld
2022-06-25  5:09     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 37/55] media: mc-entity: Add a new helper function to get a remote pad Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-15 22:38   ` Laurent Pinchart
2022-06-15 22:38     ` Laurent Pinchart
2022-06-17 11:38   ` Hans Verkuil
2022-06-17 11:38     ` Hans Verkuil
2022-06-17 11:48   ` Hans Verkuil
2022-06-17 11:48     ` Hans Verkuil
2022-06-25 17:00     ` Laurent Pinchart
2022-06-25 17:00       ` Laurent Pinchart
2022-06-25 17:28       ` Laurent Pinchart
2022-06-25 17:28         ` Laurent Pinchart
2022-07-07  6:52       ` Hans Verkuil
2022-07-07  6:52         ` Hans Verkuil
2022-07-07 11:50         ` Laurent Pinchart
2022-07-07 11:50           ` Laurent Pinchart
2022-06-17 21:34   ` Daniel Scally
2022-06-17 21:34     ` Daniel Scally
2022-06-17 22:33     ` Daniel Scally
2022-06-17 22:33       ` Daniel Scally
2022-06-17 22:40       ` Laurent Pinchart
2022-06-17 22:40         ` Laurent Pinchart
2022-06-18  9:35         ` Daniel Scally
2022-06-18  9:35           ` Daniel Scally
2022-06-25 17:34           ` Laurent Pinchart
2022-06-25 17:34             ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 38/55] media: mc-entity: Add a new helper function to get a remote pad for a pad Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-15 22:38   ` Laurent Pinchart
2022-06-15 22:38     ` Laurent Pinchart
2022-06-17 11:41   ` Hans Verkuil
2022-06-17 11:41     ` Hans Verkuil
2022-06-17 11:48     ` Laurent Pinchart
2022-06-17 11:48       ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 39/55] media: rkisp1: isp: Disallow multiple active sources Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-14 19:11 ` [PATCH 40/55] media: rkisp1: csi: Implement a V4L2 subdev for the CSI receiver Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-25  7:00   ` Dafna Hirschfeld
2022-06-25  7:00     ` Dafna Hirschfeld
2022-06-25 11:03     ` Laurent Pinchart
2022-06-25 11:03       ` Laurent Pinchart
2022-07-01  4:48       ` Dafna Hirschfeld
2022-07-01  4:48         ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 41/55] media: rkisp1: csi: Plumb the CSI RX subdev Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-15 23:10   ` Laurent Pinchart
2022-06-15 23:10     ` Laurent Pinchart
2022-06-25  7:45   ` Dafna Hirschfeld
2022-06-25  7:45     ` Dafna Hirschfeld
2022-06-25 16:07     ` Laurent Pinchart
2022-06-25 16:07       ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 42/55] media: rkisp1: Use fwnode_graph_for_each_endpoint Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-17 22:56   ` Laurent Pinchart
2022-06-17 22:56     ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 43/55] dt-bindings: media: rkisp1: Add port for parallel interface Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-17 23:13   ` Laurent Pinchart
2022-06-17 23:13     ` Laurent Pinchart
2022-07-01  5:22   ` Dafna Hirschfeld
2022-07-01  5:22     ` Dafna Hirschfeld
2022-07-01  9:19     ` Laurent Pinchart
2022-07-01  9:19       ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 44/55] media: rkisp1: Support the ISP parallel input Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-14 19:11 ` [PATCH 45/55] media: rkisp1: Add infrastructure to support ISP features Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-14 19:11 ` [PATCH 46/55] media: rkisp1: Make the internal CSI-2 receiver optional Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-14 19:11 ` [PATCH 47/55] dt-bindings: media: rkisp1: Add i.MX8MP ISP to compatible Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-17 23:14   ` Laurent Pinchart
2022-06-17 23:14     ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 48/55] media: rkisp1: Add match data for i.MX8MP ISP Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-17 23:26   ` Laurent Pinchart
2022-06-17 23:26     ` Laurent Pinchart
2022-06-26  4:05     ` Dafna Hirschfeld
2022-06-26  4:05       ` Dafna Hirschfeld
2022-06-26 11:07       ` Laurent Pinchart
2022-06-26 11:07         ` Laurent Pinchart
2022-07-04 10:36         ` paul.elder
2022-07-04 10:36           ` paul.elder
2022-06-14 19:11 ` [PATCH 49/55] media: rkisp1: Configure gasket on i.MX8MP Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-14 19:11 ` [PATCH 50/55] media: rkisp1: Add and set registers for crop for i.MX8MP Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-26 11:59   ` Laurent Pinchart
2022-06-26 11:59     ` Laurent Pinchart
2022-07-04 10:37     ` paul.elder
2022-07-04 10:37       ` paul.elder
2022-07-01  5:37   ` Dafna Hirschfeld
2022-07-01  5:37     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 51/55] media: rkisp1: Add and set registers for output size config on i.MX8MP Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-26 11:46   ` Laurent Pinchart
2022-06-26 11:46     ` Laurent Pinchart
2022-07-01  5:40   ` Dafna Hirschfeld
2022-07-01  5:40     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 52/55] media: rkisp1: Add i.MX8MP-specific registers for MI and resizer Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-07-01  5:45   ` Dafna Hirschfeld
2022-07-01  5:45     ` Dafna Hirschfeld
2022-06-14 19:11 ` [PATCH 53/55] media: rkisp1: Shift DMA buffer addresses on i.MX8MP Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-26 11:38   ` Laurent Pinchart
2022-06-26 11:38     ` Laurent Pinchart
2022-07-01  5:53     ` Dafna Hirschfeld
2022-07-01  5:53       ` Dafna Hirschfeld
2022-07-01  8:38       ` Laurent Pinchart
2022-07-01  8:38         ` Laurent Pinchart
2022-06-14 19:11 ` [PATCH 54/55] media: rkisp1: Add register definitions for the test pattern generator Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-14 19:11 ` [PATCH 55/55] media: rkisp1: Fix RSZ_CTRL bits for i.MX8MP Paul Elder
2022-06-14 19:11   ` Paul Elder
2022-06-16  8:05   ` (EXT) " Alexander Stein
2022-06-16  8:05     ` Alexander Stein
2022-06-17 23:03     ` Laurent Pinchart
2022-06-17 23:03       ` Laurent Pinchart
2022-06-26 11:40       ` Laurent Pinchart
2022-06-26 11:40         ` Laurent Pinchart
2022-07-04 10:40       ` paul.elder
2022-07-04 10:40         ` paul.elder
2022-06-16  0:19 ` [PATCH 00/55] media: rkisp1: Cleanups and add support " Laurent Pinchart
2022-06-16  0:19   ` Laurent Pinchart

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.