From patchwork Thu Aug 23 13:25:15 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573821 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5508013B6 for ; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 50B962B736 for ; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 455AA2BDF5; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 7FCA62B736 for ; Thu, 23 Aug 2018 13:28:03 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730572AbeHWQ5o (ORCPT ); Thu, 23 Aug 2018 12:57:44 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12047 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730564AbeHWQ5n (ORCPT ); Thu, 23 Aug 2018 12:57:43 -0400 X-Halon-ID: 5a1c69e9-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5a1c69e9-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:27:59 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 01/30] media: entity: Use pad as a starting point for graph walk Date: Thu, 23 Aug 2018 15:25:15 +0200 Message-Id: <20180823132544.521-2-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus With the upcoming use of the recently added has_route() media entity op, all the pads in an entity will no longer be considered interconnected. This has an effect where the media graph is traversed: the starting pad does make a difference. Prepare for this change by using pad instead of the entity as an argument for the graph walk operations. The actual graph traversal algorithm change is in further patches. Signed-off-by: Sakari Ailus --- Documentation/media/kapi/mc-core.rst | 2 +- drivers/media/media-entity.c | 17 ++++++++--------- drivers/media/platform/exynos4-is/media-dev.c | 4 ++-- drivers/media/platform/omap3isp/ispvideo.c | 2 +- drivers/media/platform/vsp1/vsp1_video.c | 2 +- drivers/media/platform/xilinx/xilinx-dma.c | 2 +- drivers/media/v4l2-core/v4l2-mc.c | 6 +++--- drivers/staging/media/davinci_vpfe/vpfe_video.c | 6 +++--- drivers/staging/media/omap4iss/iss_video.c | 4 ++-- include/media/media-entity.h | 10 ++++------ 10 files changed, 26 insertions(+), 29 deletions(-) diff --git a/Documentation/media/kapi/mc-core.rst b/Documentation/media/kapi/mc-core.rst index 0c05503eaf1fa6c7..27aefb9a778b2ad6 100644 --- a/Documentation/media/kapi/mc-core.rst +++ b/Documentation/media/kapi/mc-core.rst @@ -165,7 +165,7 @@ Drivers initiate a graph traversal by calling :c:func:`media_graph_walk_start()` The graph structure, provided by the caller, is initialized to start graph -traversal at the given entity. +traversal at the given pad in an entity. Drivers can then retrieve the next entity by calling :c:func:`media_graph_walk_next()` diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 3498551e618e5437..70679d186944a117 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -300,17 +300,16 @@ void media_graph_walk_cleanup(struct media_graph *graph) } EXPORT_SYMBOL_GPL(media_graph_walk_cleanup); -void media_graph_walk_start(struct media_graph *graph, - struct media_entity *entity) +void media_graph_walk_start(struct media_graph *graph, struct media_pad *pad) { media_entity_enum_zero(&graph->ent_enum); - media_entity_enum_set(&graph->ent_enum, entity); + media_entity_enum_set(&graph->ent_enum, pad->entity); graph->top = 0; graph->stack[graph->top].entity = NULL; - stack_push(graph, entity); - dev_dbg(entity->graph_obj.mdev->dev, - "begin graph walk at '%s'\n", entity->name); + stack_push(graph, pad->entity); + dev_dbg(pad->graph_obj.mdev->dev, + "begin graph walk at '%s':%u\n", pad->entity->name, pad->index); } EXPORT_SYMBOL_GPL(media_graph_walk_start); @@ -428,7 +427,7 @@ __must_check int __media_pipeline_start(struct media_entity *entity, goto error_graph_walk_start; } - media_graph_walk_start(&pipe->graph, entity); + media_graph_walk_start(&pipe->graph, entity->pads); while ((entity = media_graph_walk_next(graph))) { DECLARE_BITMAP(active, MEDIA_ENTITY_MAX_PADS); @@ -509,7 +508,7 @@ __must_check int __media_pipeline_start(struct media_entity *entity, * Link validation on graph failed. We revert what we did and * return the error. */ - media_graph_walk_start(graph, entity_err); + media_graph_walk_start(graph, entity_err->pads); while ((entity_err = media_graph_walk_next(graph))) { /* Sanity check for negative stream_count */ @@ -560,7 +559,7 @@ void __media_pipeline_stop(struct media_entity *entity) if (WARN_ON(!pipe)) return; - media_graph_walk_start(graph, entity); + media_graph_walk_start(graph, entity->pads); while ((entity = media_graph_walk_next(graph))) { /* Sanity check for negative stream_count */ diff --git a/drivers/media/platform/exynos4-is/media-dev.c b/drivers/media/platform/exynos4-is/media-dev.c index deb499f76412a33f..4e7aa9a37f22b904 100644 --- a/drivers/media/platform/exynos4-is/media-dev.c +++ b/drivers/media/platform/exynos4-is/media-dev.c @@ -1133,7 +1133,7 @@ static int __fimc_md_modify_pipelines(struct media_entity *entity, bool enable, * through active links. This is needed as we cannot power on/off the * subdevs in random order. */ - media_graph_walk_start(graph, entity); + media_graph_walk_start(graph, entity->pads); while ((entity = media_graph_walk_next(graph))) { if (!is_media_entity_v4l2_video_device(entity)) @@ -1148,7 +1148,7 @@ static int __fimc_md_modify_pipelines(struct media_entity *entity, bool enable, return 0; err: - media_graph_walk_start(graph, entity_err); + media_graph_walk_start(graph, entity_err->pads); while ((entity_err = media_graph_walk_next(graph))) { if (!is_media_entity_v4l2_video_device(entity_err)) diff --git a/drivers/media/platform/omap3isp/ispvideo.c b/drivers/media/platform/omap3isp/ispvideo.c index 9d228eac24ea538c..218220b0a3ebb781 100644 --- a/drivers/media/platform/omap3isp/ispvideo.c +++ b/drivers/media/platform/omap3isp/ispvideo.c @@ -238,7 +238,7 @@ static int isp_video_get_graph_data(struct isp_video *video, return ret; } - media_graph_walk_start(&graph, entity); + media_graph_walk_start(&graph, entity->pads); while ((entity = media_graph_walk_next(&graph))) { struct isp_video *__video; diff --git a/drivers/media/platform/vsp1/vsp1_video.c b/drivers/media/platform/vsp1/vsp1_video.c index 81d47a09d7bcc6b8..da75847a61f3be63 100644 --- a/drivers/media/platform/vsp1/vsp1_video.c +++ b/drivers/media/platform/vsp1/vsp1_video.c @@ -583,7 +583,7 @@ static int vsp1_video_pipeline_build(struct vsp1_pipeline *pipe, if (ret) return ret; - media_graph_walk_start(&graph, entity); + media_graph_walk_start(&graph, entity->pads); while ((entity = media_graph_walk_next(&graph))) { struct v4l2_subdev *subdev; diff --git a/drivers/media/platform/xilinx/xilinx-dma.c b/drivers/media/platform/xilinx/xilinx-dma.c index d041f94be832ae62..ba767fa707e39dc4 100644 --- a/drivers/media/platform/xilinx/xilinx-dma.c +++ b/drivers/media/platform/xilinx/xilinx-dma.c @@ -193,7 +193,7 @@ static int xvip_pipeline_validate(struct xvip_pipeline *pipe, return ret; } - media_graph_walk_start(&graph, entity); + media_graph_walk_start(&graph, entity->pads); while ((entity = media_graph_walk_next(&graph))) { struct xvip_dma *dma; diff --git a/drivers/media/v4l2-core/v4l2-mc.c b/drivers/media/v4l2-core/v4l2-mc.c index 0fc185a2ce90e80a..c8adddb878cbd3b5 100644 --- a/drivers/media/v4l2-core/v4l2-mc.c +++ b/drivers/media/v4l2-core/v4l2-mc.c @@ -260,7 +260,7 @@ static int pipeline_pm_use_count(struct media_entity *entity, { int use = 0; - media_graph_walk_start(graph, entity); + media_graph_walk_start(graph, entity->pads); while ((entity = media_graph_walk_next(graph))) { if (is_media_entity_v4l2_video_device(entity)) @@ -323,7 +323,7 @@ static int pipeline_pm_power(struct media_entity *entity, int change, if (!change) return 0; - media_graph_walk_start(graph, entity); + media_graph_walk_start(graph, entity->pads); while (!ret && (entity = media_graph_walk_next(graph))) if (is_media_entity_v4l2_subdev(entity)) @@ -332,7 +332,7 @@ static int pipeline_pm_power(struct media_entity *entity, int change, if (!ret) return ret; - media_graph_walk_start(graph, first); + media_graph_walk_start(graph, first->pads); while ((first = media_graph_walk_next(graph)) && first != entity) diff --git a/drivers/staging/media/davinci_vpfe/vpfe_video.c b/drivers/staging/media/davinci_vpfe/vpfe_video.c index 1269a983455e57c5..af0d9e81b8de1cad 100644 --- a/drivers/staging/media/davinci_vpfe/vpfe_video.c +++ b/drivers/staging/media/davinci_vpfe/vpfe_video.c @@ -150,7 +150,7 @@ static int vpfe_prepare_pipeline(struct vpfe_video_device *video) mutex_unlock(&mdev->graph_mutex); return -ENOMEM; } - media_graph_walk_start(&graph, entity); + media_graph_walk_start(&graph, entity->pads); while ((entity = media_graph_walk_next(&graph))) { if (entity == &video->video_dev.entity) continue; @@ -303,7 +303,7 @@ static int vpfe_pipeline_enable(struct vpfe_pipeline *pipe) ret = media_graph_walk_init(&pipe->graph, mdev); if (ret) goto out; - media_graph_walk_start(&pipe->graph, entity); + media_graph_walk_start(&pipe->graph, entity->pads); while ((entity = media_graph_walk_next(&pipe->graph))) { if (!is_media_entity_v4l2_subdev(entity)) @@ -345,7 +345,7 @@ static int vpfe_pipeline_disable(struct vpfe_pipeline *pipe) mdev = entity->graph_obj.mdev; mutex_lock(&mdev->graph_mutex); - media_graph_walk_start(&pipe->graph, entity); + media_graph_walk_start(&pipe->graph, entity->pads); while ((entity = media_graph_walk_next(&pipe->graph))) { diff --git a/drivers/staging/media/omap4iss/iss_video.c b/drivers/staging/media/omap4iss/iss_video.c index a3a83424a926c793..b646fe909bad64d4 100644 --- a/drivers/staging/media/omap4iss/iss_video.c +++ b/drivers/staging/media/omap4iss/iss_video.c @@ -220,7 +220,7 @@ iss_video_far_end(struct iss_video *video) return NULL; } - media_graph_walk_start(&graph, entity); + media_graph_walk_start(&graph, entity->pads); while ((entity = media_graph_walk_next(&graph))) { if (entity == &video->video.entity) @@ -900,7 +900,7 @@ iss_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) if (ret < 0) goto err_media_pipeline_start; - media_graph_walk_start(&graph, entity); + media_graph_walk_start(&graph, entity->pads); while ((entity = media_graph_walk_next(&graph))) media_entity_enum_set(&pipe->ent_enum, entity); diff --git a/include/media/media-entity.h b/include/media/media-entity.h index 3aa3d58d1d586dc2..20ff038c8aeff4b8 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -880,22 +880,20 @@ void media_graph_walk_cleanup(struct media_graph *graph); void media_entity_put(struct media_entity *entity); /** - * media_graph_walk_start - Start walking the media graph at a - * given entity + * media_graph_walk_start - Start walking the media graph at a given pad * * @graph: Media graph structure that will be used to walk the graph - * @entity: Starting entity + * @pad: Starting pad * * Before using this function, media_graph_walk_init() must be * used to allocate resources used for walking the graph. This * function initializes the graph traversal structure to walk the - * entities graph starting at the given entity. The traversal + * entities graph starting at the given pad. The traversal * structure must not be modified by the caller during graph * traversal. After the graph walk, the resources must be released * using media_graph_walk_cleanup(). */ -void media_graph_walk_start(struct media_graph *graph, - struct media_entity *entity); +void media_graph_walk_start(struct media_graph *graph, struct media_pad *pad); /** * media_graph_walk_next - Get the next entity in the graph From patchwork Thu Aug 23 13:25:16 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573825 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id AB398139B for ; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A875A2B72C for ; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 9CDA02B736; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 086BB2BDBF for ; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730559AbeHWQ5o (ORCPT ); Thu, 23 Aug 2018 12:57:44 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12057 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730568AbeHWQ5n (ORCPT ); Thu, 23 Aug 2018 12:57:43 -0400 X-Halon-ID: 5ab656b3-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5ab656b3-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:00 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 02/30] media: entity: Use pads instead of entities in the media graph walk stack Date: Thu, 23 Aug 2018 15:25:16 +0200 Message-Id: <20180823132544.521-3-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Change the media graph walk stack structure to use media pads instead of using media entities. In addition to the entity, the pad contains the information which pad in the entity are being dealt with. Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 53 ++++++++++++++++++------------------ include/media/media-entity.h | 6 ++-- 2 files changed, 29 insertions(+), 30 deletions(-) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 70679d186944a117..c5dcae6d0caf92ec 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -237,40 +237,39 @@ EXPORT_SYMBOL_GPL(media_entity_pads_init); * Graph traversal */ -static struct media_entity * -media_entity_other(struct media_entity *entity, struct media_link *link) +static struct media_pad * +media_entity_other(struct media_pad *pad, struct media_link *link) { - if (link->source->entity == entity) - return link->sink->entity; + if (link->source == pad) + return link->sink; else - return link->source->entity; + return link->source; } /* push an entity to traversal stack */ -static void stack_push(struct media_graph *graph, - struct media_entity *entity) +static void stack_push(struct media_graph *graph, struct media_pad *pad) { if (graph->top == MEDIA_ENTITY_ENUM_MAX_DEPTH - 1) { WARN_ON(1); return; } graph->top++; - graph->stack[graph->top].link = entity->links.next; - graph->stack[graph->top].entity = entity; + graph->stack[graph->top].link = pad->entity->links.next; + graph->stack[graph->top].pad = pad; } -static struct media_entity *stack_pop(struct media_graph *graph) +static struct media_pad *stack_pop(struct media_graph *graph) { - struct media_entity *entity; + struct media_pad *pad; - entity = graph->stack[graph->top].entity; + pad = graph->stack[graph->top].pad; graph->top--; - return entity; + return pad; } #define link_top(en) ((en)->stack[(en)->top].link) -#define stack_top(en) ((en)->stack[(en)->top].entity) +#define stack_top(en) ((en)->stack[(en)->top].pad) /** * media_graph_walk_init - Allocate resources for graph walk @@ -306,8 +305,8 @@ void media_graph_walk_start(struct media_graph *graph, struct media_pad *pad) media_entity_enum_set(&graph->ent_enum, pad->entity); graph->top = 0; - graph->stack[graph->top].entity = NULL; - stack_push(graph, pad->entity); + graph->stack[graph->top].pad = NULL; + stack_push(graph, pad); dev_dbg(pad->graph_obj.mdev->dev, "begin graph walk at '%s':%u\n", pad->entity->name, pad->index); } @@ -315,16 +314,16 @@ EXPORT_SYMBOL_GPL(media_graph_walk_start); static void media_graph_walk_iter(struct media_graph *graph) { - struct media_entity *entity = stack_top(graph); + struct media_pad *pad = stack_top(graph); struct media_link *link; - struct media_entity *next; + struct media_pad *next; link = list_entry(link_top(graph), typeof(*link), list); /* The link is not enabled so we do not follow. */ if (!(link->flags & MEDIA_LNK_FL_ENABLED)) { link_top(graph) = link_top(graph)->next; - dev_dbg(entity->graph_obj.mdev->dev, + dev_dbg(pad->graph_obj.mdev->dev, "walk: skipping disabled link '%s':%u -> '%s':%u\n", link->source->entity->name, link->source->index, link->sink->entity->name, link->sink->index); @@ -332,22 +331,22 @@ static void media_graph_walk_iter(struct media_graph *graph) } /* Get the entity in the other end of the link . */ - next = media_entity_other(entity, link); + next = media_entity_other(pad, link); /* Has the entity already been visited? */ - if (media_entity_enum_test_and_set(&graph->ent_enum, next)) { + if (media_entity_enum_test_and_set(&graph->ent_enum, next->entity)) { link_top(graph) = link_top(graph)->next; - dev_dbg(entity->graph_obj.mdev->dev, + dev_dbg(pad->graph_obj.mdev->dev, "walk: skipping entity '%s' (already seen)\n", - next->name); + next->entity->name); return; } /* Push the new entity to stack and start over. */ link_top(graph) = link_top(graph)->next; stack_push(graph, next); - dev_dbg(entity->graph_obj.mdev->dev, "walk: pushing '%s' on stack\n", - next->name); + dev_dbg(next->graph_obj.mdev->dev, "walk: pushing '%s':%u on stack\n", + next->entity->name, next->index); } struct media_entity *media_graph_walk_next(struct media_graph *graph) @@ -362,10 +361,10 @@ struct media_entity *media_graph_walk_next(struct media_graph *graph) * top of the stack until no more entities on the level can be * found. */ - while (link_top(graph) != &stack_top(graph)->links) + while (link_top(graph) != &stack_top(graph)->entity->links) media_graph_walk_iter(graph); - entity = stack_pop(graph); + entity = stack_pop(graph)->entity; dev_dbg(entity->graph_obj.mdev->dev, "walk: returning entity '%s'\n", entity->name); diff --git a/include/media/media-entity.h b/include/media/media-entity.h index 20ff038c8aeff4b8..c844a677a1cfbb0d 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -86,16 +86,16 @@ struct media_entity_enum { * struct media_graph - Media graph traversal state * * @stack: Graph traversal stack; the stack contains information - * on the path the media entities to be walked and the + * on the path the media pads to be walked and the * links through which they were reached. - * @stack.entity: pointer to &struct media_entity at the graph. + * @stack.pad: pointer to &struct media_pad at the graph. * @stack.link: pointer to &struct list_head. * @ent_enum: Visited entities * @top: The top of the stack */ struct media_graph { struct { - struct media_entity *entity; + struct media_pad *pad; struct list_head *link; } stack[MEDIA_ENTITY_ENUM_MAX_DEPTH]; From patchwork Thu Aug 23 13:25:17 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573831 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 2D6B01579 for ; Thu, 23 Aug 2018 13:28:06 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 25DA42B72C for ; Thu, 23 Aug 2018 13:28:06 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 198D72BDBF; Thu, 23 Aug 2018 13:28:06 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id C7B742B72C for ; Thu, 23 Aug 2018 13:28:04 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730630AbeHWQ5q (ORCPT ); Thu, 23 Aug 2018 12:57:46 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12075 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730564AbeHWQ5q (ORCPT ); Thu, 23 Aug 2018 12:57:46 -0400 X-Halon-ID: 5b348e9a-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5b348e9a-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:01 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 03/30] media: entity: Walk the graph based on pads Date: Thu, 23 Aug 2018 15:25:17 +0200 Message-Id: <20180823132544.521-4-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Instead of iterating over graph entities during the walk, iterate the pads through which the entity was first reached. This is required in order to make the entity pipeline pad-based rather than entity based. Signed-off-by: Sakari Ailus --- Documentation/media/kapi/mc-core.rst | 7 ++- drivers/media/media-entity.c | 46 ++++++++++-------- drivers/media/platform/exynos4-is/media-dev.c | 20 ++++---- drivers/media/platform/omap3isp/ispvideo.c | 17 +++---- drivers/media/platform/vsp1/vsp1_video.c | 12 ++--- drivers/media/platform/xilinx/xilinx-dma.c | 12 ++--- drivers/media/v4l2-core/v4l2-mc.c | 25 +++++----- .../staging/media/davinci_vpfe/vpfe_video.c | 47 ++++++++++--------- drivers/staging/media/omap4iss/iss_video.c | 34 +++++++------- include/media/media-entity.h | 7 +-- 10 files changed, 122 insertions(+), 105 deletions(-) diff --git a/Documentation/media/kapi/mc-core.rst b/Documentation/media/kapi/mc-core.rst index 27aefb9a778b2ad6..849b87439b7a9772 100644 --- a/Documentation/media/kapi/mc-core.rst +++ b/Documentation/media/kapi/mc-core.rst @@ -167,8 +167,11 @@ Drivers initiate a graph traversal by calling The graph structure, provided by the caller, is initialized to start graph traversal at the given pad in an entity. -Drivers can then retrieve the next entity by calling -:c:func:`media_graph_walk_next()` +Drivers can then retrieve the next pad by calling +:c:func:`media_graph_walk_next()`. Only the pad through which the entity +is first reached is returned. If the caller is interested in knowing which +further pads would be connected, the :c:func:`media_entity_has_route()` +function can be used for that. When the graph traversal is complete the function will return ``NULL``. diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index c5dcae6d0caf92ec..ec7c61dff6ae879d 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -349,9 +349,9 @@ static void media_graph_walk_iter(struct media_graph *graph) next->entity->name, next->index); } -struct media_entity *media_graph_walk_next(struct media_graph *graph) +struct media_pad *media_graph_walk_next(struct media_graph *graph) { - struct media_entity *entity; + struct media_pad *pad; if (stack_top(graph) == NULL) return NULL; @@ -364,11 +364,11 @@ struct media_entity *media_graph_walk_next(struct media_graph *graph) while (link_top(graph) != &stack_top(graph)->entity->links) media_graph_walk_iter(graph); - entity = stack_pop(graph)->entity; - dev_dbg(entity->graph_obj.mdev->dev, - "walk: returning entity '%s'\n", entity->name); + pad = stack_pop(graph); + dev_dbg(pad->graph_obj.mdev->dev, + "walk: returning pad '%s':%u\n", pad->entity->name, pad->index); - return entity; + return pad; } EXPORT_SYMBOL_GPL(media_graph_walk_next); @@ -416,7 +416,8 @@ __must_check int __media_pipeline_start(struct media_entity *entity, { struct media_device *mdev = entity->graph_obj.mdev; struct media_graph *graph = &pipe->graph; - struct media_entity *entity_err = entity; + struct media_pad *pad = entity->pads; + struct media_pad *pad_err = pad; struct media_link *link; int ret; @@ -426,9 +427,11 @@ __must_check int __media_pipeline_start(struct media_entity *entity, goto error_graph_walk_start; } - media_graph_walk_start(&pipe->graph, entity->pads); + media_graph_walk_start(&pipe->graph, pad); + + while ((pad = media_graph_walk_next(graph))) { + struct media_entity *entity = pad->entity; - while ((entity = media_graph_walk_next(graph))) { DECLARE_BITMAP(active, MEDIA_ENTITY_MAX_PADS); DECLARE_BITMAP(has_no_links, MEDIA_ENTITY_MAX_PADS); @@ -452,11 +455,11 @@ __must_check int __media_pipeline_start(struct media_entity *entity, bitmap_fill(has_no_links, entity->num_pads); list_for_each_entry(link, &entity->links, list) { - struct media_pad *pad = link->sink->entity == entity - ? link->sink : link->source; + struct media_pad *other_pad = link->sink->entity == entity + ? link->sink : link->source; /* Mark that a pad is connected by a link. */ - bitmap_clear(has_no_links, pad->index, 1); + bitmap_clear(has_no_links, other_pad->index, 1); /* * Pads that either do not need to connect or @@ -465,13 +468,13 @@ __must_check int __media_pipeline_start(struct media_entity *entity, */ if (!(pad->flags & MEDIA_PAD_FL_MUST_CONNECT) || link->flags & MEDIA_LNK_FL_ENABLED) - bitmap_set(active, pad->index, 1); + bitmap_set(active, other_pad->index, 1); /* * Link validation will only take place for * sink ends of the link that are enabled. */ - if (link->sink != pad || + if (link->sink != other_pad || !(link->flags & MEDIA_LNK_FL_ENABLED)) continue; @@ -507,9 +510,11 @@ __must_check int __media_pipeline_start(struct media_entity *entity, * Link validation on graph failed. We revert what we did and * return the error. */ - media_graph_walk_start(graph, entity_err->pads); + media_graph_walk_start(graph, pad_err); + + while ((pad_err = media_graph_walk_next(graph))) { + struct media_entity *entity_err = pad_err->entity; - while ((entity_err = media_graph_walk_next(graph))) { /* Sanity check for negative stream_count */ if (!WARN_ON_ONCE(entity_err->stream_count <= 0)) { entity_err->stream_count--; @@ -521,7 +526,7 @@ __must_check int __media_pipeline_start(struct media_entity *entity, * We haven't increased stream_count further than this * so we quit here. */ - if (entity_err == entity) + if (pad_err == pad) break; } @@ -548,8 +553,9 @@ EXPORT_SYMBOL_GPL(media_pipeline_start); void __media_pipeline_stop(struct media_entity *entity) { - struct media_graph *graph = &entity->pipe->graph; struct media_pipeline *pipe = entity->pipe; + struct media_graph *graph = &pipe->graph; + struct media_pad *pad; /* * If the following check fails, the driver has performed an @@ -560,7 +566,9 @@ void __media_pipeline_stop(struct media_entity *entity) media_graph_walk_start(graph, entity->pads); - while ((entity = media_graph_walk_next(graph))) { + while ((pad = media_graph_walk_next(graph))) { + struct media_entity *entity = pad->entity; + /* Sanity check for negative stream_count */ if (!WARN_ON_ONCE(entity->stream_count <= 0)) { entity->stream_count--; diff --git a/drivers/media/platform/exynos4-is/media-dev.c b/drivers/media/platform/exynos4-is/media-dev.c index 4e7aa9a37f22b904..0f71b56f02ceb8ab 100644 --- a/drivers/media/platform/exynos4-is/media-dev.c +++ b/drivers/media/platform/exynos4-is/media-dev.c @@ -1124,7 +1124,7 @@ static int __fimc_md_modify_pipeline(struct media_entity *entity, bool enable) static int __fimc_md_modify_pipelines(struct media_entity *entity, bool enable, struct media_graph *graph) { - struct media_entity *entity_err = entity; + struct media_pad *pad, *pad_err = entity->pads; int ret; /* @@ -1133,13 +1133,13 @@ static int __fimc_md_modify_pipelines(struct media_entity *entity, bool enable, * through active links. This is needed as we cannot power on/off the * subdevs in random order. */ - media_graph_walk_start(graph, entity->pads); + media_graph_walk_start(graph, pad_err); - while ((entity = media_graph_walk_next(graph))) { - if (!is_media_entity_v4l2_video_device(entity)) + while ((pad = media_graph_walk_next(graph))) { + if (!is_media_entity_v4l2_video_device(pad->entity)) continue; - ret = __fimc_md_modify_pipeline(entity, enable); + ret = __fimc_md_modify_pipeline(pad->entity, enable); if (ret < 0) goto err; @@ -1148,15 +1148,15 @@ static int __fimc_md_modify_pipelines(struct media_entity *entity, bool enable, return 0; err: - media_graph_walk_start(graph, entity_err->pads); + media_graph_walk_start(graph, pad_err); - while ((entity_err = media_graph_walk_next(graph))) { - if (!is_media_entity_v4l2_video_device(entity_err)) + while ((pad_err = media_graph_walk_next(graph))) { + if (!is_media_entity_v4l2_video_device(pad_err->entity)) continue; - __fimc_md_modify_pipeline(entity_err, !enable); + __fimc_md_modify_pipeline(pad_err->entity, !enable); - if (entity_err == entity) + if (pad_err == pad) break; } diff --git a/drivers/media/platform/omap3isp/ispvideo.c b/drivers/media/platform/omap3isp/ispvideo.c index 218220b0a3ebb781..1f52779249cfaf60 100644 --- a/drivers/media/platform/omap3isp/ispvideo.c +++ b/drivers/media/platform/omap3isp/ispvideo.c @@ -226,8 +226,8 @@ static int isp_video_get_graph_data(struct isp_video *video, struct isp_pipeline *pipe) { struct media_graph graph; - struct media_entity *entity = &video->video.entity; - struct media_device *mdev = entity->graph_obj.mdev; + struct media_pad *pad = video->video.entity.pads; + struct media_device *mdev = pad->entity->graph_obj.mdev; struct isp_video *far_end = NULL; int ret; @@ -238,23 +238,24 @@ static int isp_video_get_graph_data(struct isp_video *video, return ret; } - media_graph_walk_start(&graph, entity->pads); + media_graph_walk_start(&graph, pad); - while ((entity = media_graph_walk_next(&graph))) { + while ((pad = media_graph_walk_next(&graph))) { struct isp_video *__video; - media_entity_enum_set(&pipe->ent_enum, entity); + media_entity_enum_set(&pipe->ent_enum, pad->entity); if (far_end != NULL) continue; - if (entity == &video->video.entity) + if (pad == video->video.entity.pads) continue; - if (!is_media_entity_v4l2_video_device(entity)) + if (!is_media_entity_v4l2_video_device(pad->entity)) continue; - __video = to_isp_video(media_entity_to_video_device(entity)); + __video = to_isp_video(media_entity_to_video_device( + pad->entity)); if (__video->type != video->type) far_end = __video; } diff --git a/drivers/media/platform/vsp1/vsp1_video.c b/drivers/media/platform/vsp1/vsp1_video.c index da75847a61f3be63..f3e7f239e90c5f7d 100644 --- a/drivers/media/platform/vsp1/vsp1_video.c +++ b/drivers/media/platform/vsp1/vsp1_video.c @@ -573,8 +573,8 @@ static int vsp1_video_pipeline_build(struct vsp1_pipeline *pipe, struct vsp1_video *video) { struct media_graph graph; - struct media_entity *entity = &video->video.entity; - struct media_device *mdev = entity->graph_obj.mdev; + struct media_pad *pad = video->video.entity.pads; + struct media_device *mdev = pad->entity->graph_obj.mdev; unsigned int i; int ret; @@ -583,17 +583,17 @@ static int vsp1_video_pipeline_build(struct vsp1_pipeline *pipe, if (ret) return ret; - media_graph_walk_start(&graph, entity->pads); + media_graph_walk_start(&graph, pad); - while ((entity = media_graph_walk_next(&graph))) { + while ((pad = media_graph_walk_next(&graph))) { struct v4l2_subdev *subdev; struct vsp1_rwpf *rwpf; struct vsp1_entity *e; - if (!is_media_entity_v4l2_subdev(entity)) + if (!is_media_entity_v4l2_subdev(pad->entity)) continue; - subdev = media_entity_to_v4l2_subdev(entity); + subdev = media_entity_to_v4l2_subdev(pad->entity); e = to_vsp1_entity(subdev); list_add_tail(&e->list_pipe, &pipe->entities); e->pipe = pipe; diff --git a/drivers/media/platform/xilinx/xilinx-dma.c b/drivers/media/platform/xilinx/xilinx-dma.c index ba767fa707e39dc4..9f0a53238d510fce 100644 --- a/drivers/media/platform/xilinx/xilinx-dma.c +++ b/drivers/media/platform/xilinx/xilinx-dma.c @@ -178,8 +178,8 @@ static int xvip_pipeline_validate(struct xvip_pipeline *pipe, struct xvip_dma *start) { struct media_graph graph; - struct media_entity *entity = &start->video.entity; - struct media_device *mdev = entity->graph_obj.mdev; + struct media_pad *pad = start->video.entity.pads; + struct media_device *mdev = pad->entity->graph_obj.mdev; unsigned int num_inputs = 0; unsigned int num_outputs = 0; int ret; @@ -193,15 +193,15 @@ static int xvip_pipeline_validate(struct xvip_pipeline *pipe, return ret; } - media_graph_walk_start(&graph, entity->pads); + media_graph_walk_start(&graph, pad); - while ((entity = media_graph_walk_next(&graph))) { + while ((pad = media_graph_walk_next(&graph))) { struct xvip_dma *dma; - if (entity->function != MEDIA_ENT_F_IO_V4L) + if (pad->entity->function != MEDIA_ENT_F_IO_V4L) continue; - dma = to_xvip_dma(media_entity_to_video_device(entity)); + dma = to_xvip_dma(media_entity_to_video_device(pad->entity)); if (dma->pad.flags & MEDIA_PAD_FL_SINK) { pipe->output = dma; diff --git a/drivers/media/v4l2-core/v4l2-mc.c b/drivers/media/v4l2-core/v4l2-mc.c index c8adddb878cbd3b5..d923bb344b6aeb97 100644 --- a/drivers/media/v4l2-core/v4l2-mc.c +++ b/drivers/media/v4l2-core/v4l2-mc.c @@ -258,13 +258,14 @@ EXPORT_SYMBOL_GPL(v4l_vb2q_enable_media_source); static int pipeline_pm_use_count(struct media_entity *entity, struct media_graph *graph) { + struct media_pad *pad; int use = 0; media_graph_walk_start(graph, entity->pads); - while ((entity = media_graph_walk_next(graph))) { - if (is_media_entity_v4l2_video_device(entity)) - use += entity->use_count; + while ((pad = media_graph_walk_next(graph))) { + if (is_media_entity_v4l2_video_device(pad->entity)) + use += pad->entity->use_count; } return use; @@ -317,7 +318,7 @@ static int pipeline_pm_power_one(struct media_entity *entity, int change) static int pipeline_pm_power(struct media_entity *entity, int change, struct media_graph *graph) { - struct media_entity *first = entity; + struct media_pad *tmp_pad, *pad; int ret = 0; if (!change) @@ -325,19 +326,19 @@ static int pipeline_pm_power(struct media_entity *entity, int change, media_graph_walk_start(graph, entity->pads); - while (!ret && (entity = media_graph_walk_next(graph))) - if (is_media_entity_v4l2_subdev(entity)) - ret = pipeline_pm_power_one(entity, change); + while (!ret && (pad = media_graph_walk_next(graph))) + if (is_media_entity_v4l2_subdev(pad->entity)) + ret = pipeline_pm_power_one(pad->entity, change); if (!ret) return ret; - media_graph_walk_start(graph, first->pads); + media_graph_walk_start(graph, entity->pads); - while ((first = media_graph_walk_next(graph)) - && first != entity) - if (is_media_entity_v4l2_subdev(first)) - pipeline_pm_power_one(first, -change); + while ((tmp_pad = media_graph_walk_next(graph)) + && tmp_pad != pad) + if (is_media_entity_v4l2_subdev(tmp_pad->entity)) + pipeline_pm_power_one(tmp_pad->entity, -change); return ret; } diff --git a/drivers/staging/media/davinci_vpfe/vpfe_video.c b/drivers/staging/media/davinci_vpfe/vpfe_video.c index af0d9e81b8de1cad..34f3754a9dea9a45 100644 --- a/drivers/staging/media/davinci_vpfe/vpfe_video.c +++ b/drivers/staging/media/davinci_vpfe/vpfe_video.c @@ -130,8 +130,8 @@ __vpfe_video_get_format(struct vpfe_video_device *video, static int vpfe_prepare_pipeline(struct vpfe_video_device *video) { struct media_graph graph; - struct media_entity *entity = &video->video_dev.entity; - struct media_device *mdev = entity->graph_obj.mdev; + struct media_pad *pad = video->video_dev.entity.pads; + struct media_device *mdev = pad->entity->graph_obj.mdev; struct vpfe_pipeline *pipe = &video->pipe; struct vpfe_video_device *far_end = NULL; int ret; @@ -150,13 +150,14 @@ static int vpfe_prepare_pipeline(struct vpfe_video_device *video) mutex_unlock(&mdev->graph_mutex); return -ENOMEM; } - media_graph_walk_start(&graph, entity->pads); - while ((entity = media_graph_walk_next(&graph))) { - if (entity == &video->video_dev.entity) + media_graph_walk_start(&graph, pad); + while ((pad = media_graph_walk_next(&graph))) { + if (pad->entity == &video->video_dev.entity) continue; - if (!is_media_entity_v4l2_video_device(entity)) + if (!is_media_entity_v4l2_video_device(pad->entity)) continue; - far_end = to_vpfe_video(media_entity_to_video_device(entity)); + far_end = to_vpfe_video(media_entity_to_video_device( + pad->entity)); if (far_end->type == V4L2_BUF_TYPE_VIDEO_OUTPUT) pipe->inputs[pipe->input_num++] = far_end; else @@ -288,27 +289,27 @@ static int vpfe_video_validate_pipeline(struct vpfe_pipeline *pipe) */ static int vpfe_pipeline_enable(struct vpfe_pipeline *pipe) { - struct media_entity *entity; + struct media_pad *pad; struct v4l2_subdev *subdev; struct media_device *mdev; int ret; if (pipe->state == VPFE_PIPELINE_STREAM_CONTINUOUS) - entity = vpfe_get_input_entity(pipe->outputs[0]); + pad = vpfe_get_input_entity(pipe->outputs[0])->pads; else - entity = &pipe->inputs[0]->video_dev.entity; + pad = pipe->inputs[0]->video_dev.entity.pads; - mdev = entity->graph_obj.mdev; + mdev = pad->graph_obj.mdev; mutex_lock(&mdev->graph_mutex); ret = media_graph_walk_init(&pipe->graph, mdev); if (ret) goto out; - media_graph_walk_start(&pipe->graph, entity->pads); - while ((entity = media_graph_walk_next(&pipe->graph))) { + media_graph_walk_start(&pipe->graph, pad); + while ((pad = media_graph_walk_next(&pipe->graph))) { - if (!is_media_entity_v4l2_subdev(entity)) + if (!is_media_entity_v4l2_subdev(pad->entity)) continue; - subdev = media_entity_to_v4l2_subdev(entity); + subdev = media_entity_to_v4l2_subdev(pad->entity); ret = v4l2_subdev_call(subdev, video, s_stream, 1); if (ret < 0 && ret != -ENOIOCTLCMD) break; @@ -333,25 +334,25 @@ static int vpfe_pipeline_enable(struct vpfe_pipeline *pipe) */ static int vpfe_pipeline_disable(struct vpfe_pipeline *pipe) { - struct media_entity *entity; + struct media_pad *pad; struct v4l2_subdev *subdev; struct media_device *mdev; int ret = 0; if (pipe->state == VPFE_PIPELINE_STREAM_CONTINUOUS) - entity = vpfe_get_input_entity(pipe->outputs[0]); + pad = vpfe_get_input_entity(pipe->outputs[0])->pads; else - entity = &pipe->inputs[0]->video_dev.entity; + pad = pipe->inputs[0]->video_dev.entity.pads; - mdev = entity->graph_obj.mdev; + mdev = pad->graph_obj.mdev; mutex_lock(&mdev->graph_mutex); - media_graph_walk_start(&pipe->graph, entity->pads); + media_graph_walk_start(&pipe->graph, pad); - while ((entity = media_graph_walk_next(&pipe->graph))) { + while ((pad = media_graph_walk_next(&pipe->graph))) { - if (!is_media_entity_v4l2_subdev(entity)) + if (!is_media_entity_v4l2_subdev(pad->entity)) continue; - subdev = media_entity_to_v4l2_subdev(entity); + subdev = media_entity_to_v4l2_subdev(pad->entity); ret = v4l2_subdev_call(subdev, video, s_stream, 0); if (ret < 0 && ret != -ENOIOCTLCMD) break; diff --git a/drivers/staging/media/omap4iss/iss_video.c b/drivers/staging/media/omap4iss/iss_video.c index b646fe909bad64d4..28efafa0621ef010 100644 --- a/drivers/staging/media/omap4iss/iss_video.c +++ b/drivers/staging/media/omap4iss/iss_video.c @@ -209,8 +209,8 @@ static struct iss_video * iss_video_far_end(struct iss_video *video) { struct media_graph graph; - struct media_entity *entity = &video->video.entity; - struct media_device *mdev = entity->graph_obj.mdev; + struct media_pad *pad = video->video.entity.pads; + struct media_device *mdev = pad->entity->graph_obj.mdev; struct iss_video *far_end = NULL; mutex_lock(&mdev->graph_mutex); @@ -220,16 +220,17 @@ iss_video_far_end(struct iss_video *video) return NULL; } - media_graph_walk_start(&graph, entity->pads); + media_graph_walk_start(&graph, pad); - while ((entity = media_graph_walk_next(&graph))) { - if (entity == &video->video.entity) + while ((pad = media_graph_walk_next(&graph))) { + if (pad->entity == &video->video.entity) continue; - if (!is_media_entity_v4l2_video_device(entity)) + if (!is_media_entity_v4l2_video_device(pad->entity)) continue; - far_end = to_iss_video(media_entity_to_video_device(entity)); + far_end = to_iss_video(media_entity_to_video_device( + pad->entity)); if (far_end->type != video->type) break; @@ -863,7 +864,7 @@ iss_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) struct iss_video_fh *vfh = to_iss_video_fh(fh); struct iss_video *video = video_drvdata(file); struct media_graph graph; - struct media_entity *entity = &video->video.entity; + struct media_pad *pad = video->video.entity.pads; enum iss_pipeline_state state; struct iss_pipeline *pipe; struct iss_video *far_end; @@ -879,30 +880,31 @@ iss_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) * Start streaming on the pipeline. No link touching an entity in the * pipeline can be activated or deactivated once streaming is started. */ - pipe = entity->pipe - ? to_iss_pipeline(entity) : &video->pipe; + pipe = pad->entity->pipe + ? to_iss_pipeline(pad->entity) : &video->pipe; pipe->external = NULL; pipe->external_rate = 0; pipe->external_bpp = 0; - ret = media_entity_enum_init(&pipe->ent_enum, entity->graph_obj.mdev); + ret = media_entity_enum_init(&pipe->ent_enum, + pad->entity->graph_obj.mdev); if (ret) goto err_graph_walk_init; - ret = media_graph_walk_init(&graph, entity->graph_obj.mdev); + ret = media_graph_walk_init(&graph, pad->entity->graph_obj.mdev); if (ret) goto err_graph_walk_init; if (video->iss->pdata->set_constraints) video->iss->pdata->set_constraints(video->iss, true); - ret = media_pipeline_start(entity, &pipe->pipe); + ret = media_pipeline_start(pad->entity, &pipe->pipe); if (ret < 0) goto err_media_pipeline_start; - media_graph_walk_start(&graph, entity->pads); - while ((entity = media_graph_walk_next(&graph))) - media_entity_enum_set(&pipe->ent_enum, entity); + media_graph_walk_start(&graph, pad); + while ((pad = media_graph_walk_next(&graph))) + media_entity_enum_set(&pipe->ent_enum, pad->entity); /* * Verify that the currently configured format matches the output of diff --git a/include/media/media-entity.h b/include/media/media-entity.h index c844a677a1cfbb0d..fad1776cbaadbbab 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -904,10 +904,11 @@ void media_graph_walk_start(struct media_graph *graph, struct media_pad *pad); * The graph structure must have been previously initialized with a call to * media_graph_walk_start(). * - * Return: returns the next entity in the graph or %NULL if the whole graph - * have been traversed. + * Return: returns the next pad in the graph or %NULL if the whole + * graph have been traversed. The pad which is returned is the pad + * through which a new entity is reached when parsing the graph. */ -struct media_entity *media_graph_walk_next(struct media_graph *graph); +struct media_pad *media_graph_walk_next(struct media_graph *graph); /** * media_pipeline_start - Mark a pipeline as streaming From patchwork Thu Aug 23 13:25:18 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573829 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 07906139B for ; Thu, 23 Aug 2018 13:28:06 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 011252BDBF for ; Thu, 23 Aug 2018 13:28:06 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id E972C2BDC7; Thu, 23 Aug 2018 13:28:05 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 8CFEF2B736 for ; Thu, 23 Aug 2018 13:28:05 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730609AbeHWQ5q (ORCPT ); Thu, 23 Aug 2018 12:57:46 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12102 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730611AbeHWQ5q (ORCPT ); Thu, 23 Aug 2018 12:57:46 -0400 X-Halon-ID: 5c23c16b-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5c23c16b-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:02 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 04/30] v4l: mc: Start walk from a specific pad in use count calculation Date: Thu, 23 Aug 2018 15:25:18 +0200 Message-Id: <20180823132544.521-5-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus With the addition of the recent has_route() media entity op, the pads of a media entity are no longer all interconnected. This has to be taken into account in power management. Prepare for the addition of a helper function supporting S_ROUTING. Signed-off-by: Sakari Ailus --- drivers/media/v4l2-core/v4l2-mc.c | 25 ++++++++++++------------- 1 file changed, 12 insertions(+), 13 deletions(-) diff --git a/drivers/media/v4l2-core/v4l2-mc.c b/drivers/media/v4l2-core/v4l2-mc.c index d923bb344b6aeb97..f702cac5205b3447 100644 --- a/drivers/media/v4l2-core/v4l2-mc.c +++ b/drivers/media/v4l2-core/v4l2-mc.c @@ -251,17 +251,16 @@ EXPORT_SYMBOL_GPL(v4l_vb2q_enable_media_source); /* * pipeline_pm_use_count - Count the number of users of a pipeline - * @entity: The entity + * @pad: The pad * * Return the total number of users of all video device nodes in the pipeline. */ -static int pipeline_pm_use_count(struct media_entity *entity, - struct media_graph *graph) +static int pipeline_pm_use_count(struct media_pad *pad, + struct media_graph *graph) { - struct media_pad *pad; int use = 0; - media_graph_walk_start(graph, entity->pads); + media_graph_walk_start(graph, pad); while ((pad = media_graph_walk_next(graph))) { if (is_media_entity_v4l2_video_device(pad->entity)) @@ -307,7 +306,7 @@ static int pipeline_pm_power_one(struct media_entity *entity, int change) /* * pipeline_pm_power - Apply power change to all entities in a pipeline - * @entity: The entity + * @pad: The pad * @change: Use count change * * Walk the pipeline to update the use count and the power state of all non-node @@ -315,16 +314,16 @@ static int pipeline_pm_power_one(struct media_entity *entity, int change) * * Return 0 on success or a negative error code on failure. */ -static int pipeline_pm_power(struct media_entity *entity, int change, +static int pipeline_pm_power(struct media_pad *pad, int change, struct media_graph *graph) { - struct media_pad *tmp_pad, *pad; + struct media_pad *tmp_pad, *first = pad; int ret = 0; if (!change) return 0; - media_graph_walk_start(graph, entity->pads); + media_graph_walk_start(graph, pad); while (!ret && (pad = media_graph_walk_next(graph))) if (is_media_entity_v4l2_subdev(pad->entity)) @@ -333,7 +332,7 @@ static int pipeline_pm_power(struct media_entity *entity, int change, if (!ret) return ret; - media_graph_walk_start(graph, entity->pads); + media_graph_walk_start(graph, first); while ((tmp_pad = media_graph_walk_next(graph)) && tmp_pad != pad) @@ -356,7 +355,7 @@ int v4l2_pipeline_pm_use(struct media_entity *entity, int use) WARN_ON(entity->use_count < 0); /* Apply power change to connected non-nodes. */ - ret = pipeline_pm_power(entity, change, &mdev->pm_count_walk); + ret = pipeline_pm_power(entity->pads, change, &mdev->pm_count_walk); if (ret < 0) entity->use_count -= change; @@ -370,8 +369,8 @@ int v4l2_pipeline_link_notify(struct media_link *link, u32 flags, unsigned int notification) { struct media_graph *graph = &link->graph_obj.mdev->pm_count_walk; - struct media_entity *source = link->source->entity; - struct media_entity *sink = link->sink->entity; + struct media_pad *source = link->source; + struct media_pad *sink = link->sink; int source_use; int sink_use; int ret = 0; From patchwork Thu Aug 23 13:25:19 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573837 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 1704A139B for ; Thu, 23 Aug 2018 13:28:08 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 10E352B72C for ; Thu, 23 Aug 2018 13:28:08 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 04F302BDF5; Thu, 23 Aug 2018 13:28:08 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 7CD692B72C for ; Thu, 23 Aug 2018 13:28:06 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730622AbeHWQ5r (ORCPT ); Thu, 23 Aug 2018 12:57:47 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12130 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730611AbeHWQ5r (ORCPT ); Thu, 23 Aug 2018 12:57:47 -0400 X-Halon-ID: 5cbbda0c-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5cbbda0c-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:03 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 05/30] media: entity: Move the pipeline from entity to pads Date: Thu, 23 Aug 2018 15:25:19 +0200 Message-Id: <20180823132544.521-6-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus This moves the pipe and stream_count fields from struct media_entity to struct media_pad. Effectively streams become pad-specific rather than being stream specific, allowing several independent streams to traverse a single entity. Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 61 ++++++++++++------- drivers/media/platform/exynos4-is/fimc-isp.c | 2 +- drivers/media/platform/exynos4-is/fimc-lite.c | 2 +- drivers/media/platform/omap3isp/isp.c | 2 +- drivers/media/platform/omap3isp/ispvideo.c | 2 +- drivers/media/platform/omap3isp/ispvideo.h | 2 +- drivers/media/platform/rcar-vin/rcar-dma.c | 2 +- drivers/media/platform/xilinx/xilinx-dma.c | 2 +- drivers/media/platform/xilinx/xilinx-dma.h | 2 +- drivers/staging/media/imx/imx-media-utils.c | 2 +- drivers/staging/media/omap4iss/iss.c | 2 +- drivers/staging/media/omap4iss/iss_video.c | 2 +- drivers/staging/media/omap4iss/iss_video.h | 2 +- include/media/media-entity.h | 17 ++++-- 14 files changed, 61 insertions(+), 41 deletions(-) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index ec7c61dff6ae879d..239036a7582cbc95 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -419,7 +419,7 @@ __must_check int __media_pipeline_start(struct media_entity *entity, struct media_pad *pad = entity->pads; struct media_pad *pad_err = pad; struct media_link *link; - int ret; + int ret = 0; if (!pipe->streaming_count++) { ret = media_graph_walk_init(&pipe->graph, mdev); @@ -431,21 +431,27 @@ __must_check int __media_pipeline_start(struct media_entity *entity, while ((pad = media_graph_walk_next(graph))) { struct media_entity *entity = pad->entity; + unsigned int i; + bool skip_validation = pad->pipe; DECLARE_BITMAP(active, MEDIA_ENTITY_MAX_PADS); DECLARE_BITMAP(has_no_links, MEDIA_ENTITY_MAX_PADS); - entity->stream_count++; + for (i = 0; i < entity->num_pads; i++) { + struct media_pad *iter = &entity->pads[i]; - if (WARN_ON(entity->pipe && entity->pipe != pipe)) { - ret = -EBUSY; - goto error; + if (iter->pipe && WARN_ON(iter->pipe != pipe)) + ret = -EBUSY; + else + iter->pipe = pipe; + iter->stream_count++; } - entity->pipe = pipe; + if (ret) + goto error; /* Already streaming --- no need to check. */ - if (entity->stream_count > 1) + if (skip_validation) continue; if (!entity->ops || !entity->ops->link_validate) @@ -514,19 +520,24 @@ __must_check int __media_pipeline_start(struct media_entity *entity, while ((pad_err = media_graph_walk_next(graph))) { struct media_entity *entity_err = pad_err->entity; + unsigned int i; + + for (i = 0; i < entity_err->num_pads; i++) { + struct media_pad *iter = &entity_err->pads[i]; - /* Sanity check for negative stream_count */ - if (!WARN_ON_ONCE(entity_err->stream_count <= 0)) { - entity_err->stream_count--; - if (entity_err->stream_count == 0) - entity_err->pipe = NULL; + /* Sanity check for negative stream_count */ + if (!WARN_ON_ONCE(iter->stream_count <= 0)) { + --iter->stream_count; + if (iter->stream_count == 0) + iter->pipe = NULL; + } } /* * We haven't increased stream_count further than this * so we quit here. */ - if (pad_err == pad) + if (pad_err->entity == pad->entity) break; } @@ -553,7 +564,7 @@ EXPORT_SYMBOL_GPL(media_pipeline_start); void __media_pipeline_stop(struct media_entity *entity) { - struct media_pipeline *pipe = entity->pipe; + struct media_pipeline *pipe = entity->pads->pipe; struct media_graph *graph = &pipe->graph; struct media_pad *pad; @@ -567,13 +578,17 @@ void __media_pipeline_stop(struct media_entity *entity) media_graph_walk_start(graph, entity->pads); while ((pad = media_graph_walk_next(graph))) { - struct media_entity *entity = pad->entity; + unsigned int i; - /* Sanity check for negative stream_count */ - if (!WARN_ON_ONCE(entity->stream_count <= 0)) { - entity->stream_count--; - if (entity->stream_count == 0) - entity->pipe = NULL; + for (i = 0; i < entity->num_pads; i++) { + struct media_pad *iter = &entity->pads[i]; + + /* Sanity check for negative stream_count */ + if (!WARN_ON_ONCE(iter->stream_count <= 0)) { + iter->stream_count--; + if (iter->stream_count == 0) + iter->pipe = NULL; + } } } @@ -839,7 +854,7 @@ int __media_entity_setup_link(struct media_link *link, u32 flags) { const u32 mask = MEDIA_LNK_FL_ENABLED; struct media_device *mdev; - struct media_entity *source, *sink; + struct media_pad *source, *sink; int ret = -EBUSY; if (link == NULL) @@ -855,8 +870,8 @@ int __media_entity_setup_link(struct media_link *link, u32 flags) if (link->flags == flags) return 0; - source = link->source->entity; - sink = link->sink->entity; + source = link->source; + sink = link->sink; if (!(link->flags & MEDIA_LNK_FL_DYNAMIC) && (source->stream_count || sink->stream_count)) diff --git a/drivers/media/platform/exynos4-is/fimc-isp.c b/drivers/media/platform/exynos4-is/fimc-isp.c index 9a48c0f69320ba35..79d128a57e87fd58 100644 --- a/drivers/media/platform/exynos4-is/fimc-isp.c +++ b/drivers/media/platform/exynos4-is/fimc-isp.c @@ -229,7 +229,7 @@ static int fimc_isp_subdev_set_fmt(struct v4l2_subdev *sd, } } } else { - if (sd->entity.stream_count == 0) { + if (sd->entity.pads->stream_count == 0) { if (fmt->pad == FIMC_ISP_SD_PAD_SINK) { struct v4l2_subdev_format format = *fmt; diff --git a/drivers/media/platform/exynos4-is/fimc-lite.c b/drivers/media/platform/exynos4-is/fimc-lite.c index 70d5f5586a5d5ca6..f486eeed805b0bbc 100644 --- a/drivers/media/platform/exynos4-is/fimc-lite.c +++ b/drivers/media/platform/exynos4-is/fimc-lite.c @@ -1096,7 +1096,7 @@ static int fimc_lite_subdev_set_fmt(struct v4l2_subdev *sd, mutex_lock(&fimc->lock); if ((atomic_read(&fimc->out_path) == FIMC_IO_ISP && - sd->entity.stream_count > 0) || + sd->entity.pads->stream_count > 0) || (atomic_read(&fimc->out_path) == FIMC_IO_DMA && vb2_is_busy(&fimc->vb_queue))) { mutex_unlock(&fimc->lock); diff --git a/drivers/media/platform/omap3isp/isp.c b/drivers/media/platform/omap3isp/isp.c index 842e2235047d9c63..c487efe8c153942b 100644 --- a/drivers/media/platform/omap3isp/isp.c +++ b/drivers/media/platform/omap3isp/isp.c @@ -927,7 +927,7 @@ static int isp_pipeline_is_last(struct media_entity *me) struct isp_pipeline *pipe; struct media_pad *pad; - if (!me->pipe) + if (!me->pads->pipe) return 0; pipe = to_isp_pipeline(me); if (pipe->stream_state == ISP_PIPELINE_STREAM_STOPPED) diff --git a/drivers/media/platform/omap3isp/ispvideo.c b/drivers/media/platform/omap3isp/ispvideo.c index 1f52779249cfaf60..5ac7ac8c98d52ac8 100644 --- a/drivers/media/platform/omap3isp/ispvideo.c +++ b/drivers/media/platform/omap3isp/ispvideo.c @@ -1102,7 +1102,7 @@ isp_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) /* Start streaming on the pipeline. No link touching an entity in the * pipeline can be activated or deactivated once streaming is started. */ - pipe = video->video.entity.pipe + pipe = video->video.entity.pads->pipe ? to_isp_pipeline(&video->video.entity) : &video->pipe; ret = media_entity_enum_init(&pipe->ent_enum, &video->isp->media_dev); diff --git a/drivers/media/platform/omap3isp/ispvideo.h b/drivers/media/platform/omap3isp/ispvideo.h index f6a2082b4a0a7708..8f4146c25a1b1293 100644 --- a/drivers/media/platform/omap3isp/ispvideo.h +++ b/drivers/media/platform/omap3isp/ispvideo.h @@ -103,7 +103,7 @@ struct isp_pipeline { }; #define to_isp_pipeline(__e) \ - container_of((__e)->pipe, struct isp_pipeline, pipe) + container_of((__e)->pads->pipe, struct isp_pipeline, pipe) static inline int isp_pipeline_ready(struct isp_pipeline *pipe) { diff --git a/drivers/media/platform/rcar-vin/rcar-dma.c b/drivers/media/platform/rcar-vin/rcar-dma.c index 92323310f7352147..e749096926f34d4a 100644 --- a/drivers/media/platform/rcar-vin/rcar-dma.c +++ b/drivers/media/platform/rcar-vin/rcar-dma.c @@ -1128,7 +1128,7 @@ static int rvin_set_stream(struct rvin_dev *vin, int on) */ mdev = vin->vdev.entity.graph_obj.mdev; mutex_lock(&mdev->graph_mutex); - pipe = sd->entity.pipe ? sd->entity.pipe : &vin->vdev.pipe; + pipe = sd->entity.pads->pipe ? sd->entity.pads->pipe : &vin->vdev.pipe; ret = __media_pipeline_start(&vin->vdev.entity, pipe); mutex_unlock(&mdev->graph_mutex); if (ret) diff --git a/drivers/media/platform/xilinx/xilinx-dma.c b/drivers/media/platform/xilinx/xilinx-dma.c index 9f0a53238d510fce..9ea9a58eec632b7b 100644 --- a/drivers/media/platform/xilinx/xilinx-dma.c +++ b/drivers/media/platform/xilinx/xilinx-dma.c @@ -406,7 +406,7 @@ static int xvip_dma_start_streaming(struct vb2_queue *vq, unsigned int count) * Use the pipeline object embedded in the first DMA object that starts * streaming. */ - pipe = dma->video.entity.pipe + pipe = dma->video.entity.pads->pipe ? to_xvip_pipeline(&dma->video.entity) : &dma->pipe; ret = media_pipeline_start(&dma->video.entity, &pipe->pipe); diff --git a/drivers/media/platform/xilinx/xilinx-dma.h b/drivers/media/platform/xilinx/xilinx-dma.h index e95d136c153a8f5f..c12e053ff41eed1c 100644 --- a/drivers/media/platform/xilinx/xilinx-dma.h +++ b/drivers/media/platform/xilinx/xilinx-dma.h @@ -50,7 +50,7 @@ struct xvip_pipeline { static inline struct xvip_pipeline *to_xvip_pipeline(struct media_entity *e) { - return container_of(e->pipe, struct xvip_pipeline, pipe); + return container_of(e->pads->pipe, struct xvip_pipeline, pipe); } /** diff --git a/drivers/staging/media/imx/imx-media-utils.c b/drivers/staging/media/imx/imx-media-utils.c index 8aa13403b09d15f6..1cfa77a96e610f6c 100644 --- a/drivers/staging/media/imx/imx-media-utils.c +++ b/drivers/staging/media/imx/imx-media-utils.c @@ -917,7 +917,7 @@ int imx_media_pipeline_set_stream(struct imx_media_dev *imxmd, __media_pipeline_stop(entity); } else { v4l2_subdev_call(sd, video, s_stream, 0); - if (entity->pipe) + if (entity->pads->pipe) __media_pipeline_stop(entity); } diff --git a/drivers/staging/media/omap4iss/iss.c b/drivers/staging/media/omap4iss/iss.c index b1036baebb0357e7..6785363c09e9ba43 100644 --- a/drivers/staging/media/omap4iss/iss.c +++ b/drivers/staging/media/omap4iss/iss.c @@ -547,7 +547,7 @@ static int iss_pipeline_is_last(struct media_entity *me) struct iss_pipeline *pipe; struct media_pad *pad; - if (!me->pipe) + if (!me->pads->pipe) return 0; pipe = to_iss_pipeline(me); if (pipe->stream_state == ISS_PIPELINE_STREAM_STOPPED) diff --git a/drivers/staging/media/omap4iss/iss_video.c b/drivers/staging/media/omap4iss/iss_video.c index 28efafa0621ef010..d1d91a79992a61bc 100644 --- a/drivers/staging/media/omap4iss/iss_video.c +++ b/drivers/staging/media/omap4iss/iss_video.c @@ -880,7 +880,7 @@ iss_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) * Start streaming on the pipeline. No link touching an entity in the * pipeline can be activated or deactivated once streaming is started. */ - pipe = pad->entity->pipe + pipe = pad->pipe ? to_iss_pipeline(pad->entity) : &video->pipe; pipe->external = NULL; pipe->external_rate = 0; diff --git a/drivers/staging/media/omap4iss/iss_video.h b/drivers/staging/media/omap4iss/iss_video.h index d7e05d04512c5176..8e57a92a622c4145 100644 --- a/drivers/staging/media/omap4iss/iss_video.h +++ b/drivers/staging/media/omap4iss/iss_video.h @@ -98,7 +98,7 @@ struct iss_pipeline { }; #define to_iss_pipeline(__e) \ - container_of((__e)->pipe, struct iss_pipeline, pipe) + container_of((__e)->pads->pipe, struct iss_pipeline, pipe) static inline int iss_pipeline_ready(struct iss_pipeline *pipe) { diff --git a/include/media/media-entity.h b/include/media/media-entity.h index fad1776cbaadbbab..4f68638153679a36 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -160,14 +160,24 @@ struct media_link { * * @graph_obj: Embedded structure containing the media object common data * @entity: Entity this pad belongs to + * @pipe: Pipeline this entity belongs to. + * @stream_count: Stream count for the entity. * @index: Pad index in the entity pads array, numbered from 0 to n * @flags: Pad flags, as defined in * :ref:`include/uapi/linux/media.h ` * (seek for ``MEDIA_PAD_FL_*``) + * .. note:: + * + * @stream_count reference counts must never be negative, but are + * signed integers on purpose: a simple ``WARN_ON(<0)`` check can + * be used to detect reference count bugs that would make them + * negative. */ struct media_pad { struct media_gobj graph_obj; /* must be first field in struct */ struct media_entity *entity; + struct media_pipeline *pipe; + int stream_count; u16 index; unsigned long flags; }; @@ -244,9 +254,7 @@ enum media_entity_type { * @pads: Pads array with the size defined by @num_pads. * @links: List of data links. * @ops: Entity operations. - * @stream_count: Stream count for the entity. * @use_count: Use count for the entity. - * @pipe: Pipeline this entity belongs to. * @info: Union with devnode information. Kept just for backward * compatibility. * @info.dev: Contains device major and minor info. @@ -259,7 +267,7 @@ enum media_entity_type { * * .. note:: * - * @stream_count and @use_count reference counts must never be + * @use_count reference counts must never be * negative, but are signed integers on purpose: a simple ``WARN_ON(<0)`` * check can be used to detect reference count bugs that would make them * negative. @@ -281,11 +289,8 @@ struct media_entity { const struct media_entity_operations *ops; - int stream_count; int use_count; - struct media_pipeline *pipe; - union { struct { u32 major; From patchwork Thu Aug 23 13:25:20 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573841 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id AEF991579 for ; Thu, 23 Aug 2018 13:28:09 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A8EC62B736 for ; Thu, 23 Aug 2018 13:28:09 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 9D5592BE0E; Thu, 23 Aug 2018 13:28:09 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 321972B72C for ; Thu, 23 Aug 2018 13:28:08 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730675AbeHWQ5t (ORCPT ); Thu, 23 Aug 2018 12:57:49 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12145 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730648AbeHWQ5t (ORCPT ); Thu, 23 Aug 2018 12:57:49 -0400 X-Halon-ID: 5d65e81a-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5d65e81a-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:04 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 06/30] media: entity: Use pad as the starting point for a pipeline Date: Thu, 23 Aug 2018 15:25:20 +0200 Message-Id: <20180823132544.521-7-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus The pipeline will be moved from the entity to the pads; reflect this in the media pipeline function API. Signed-off-by: Sakari Ailus Signed-off-by: Niklas Söderlund --- Documentation/media/kapi/mc-core.rst | 6 ++-- drivers/media/media-entity.c | 25 +++++++------- drivers/media/pci/intel/ipu3/ipu3-cio2.c | 6 ++-- .../media/platform/exynos4-is/fimc-capture.c | 8 ++--- .../platform/exynos4-is/fimc-isp-video.c | 8 ++--- drivers/media/platform/exynos4-is/fimc-lite.c | 8 ++--- drivers/media/platform/omap3isp/ispvideo.c | 6 ++-- .../media/platform/qcom/camss/camss-video.c | 6 ++-- drivers/media/platform/rcar-vin/rcar-dma.c | 6 ++-- .../media/platform/s3c-camif/camif-capture.c | 6 ++-- drivers/media/platform/vimc/vimc-capture.c | 6 ++-- drivers/media/platform/vsp1/vsp1_video.c | 6 ++-- drivers/media/platform/xilinx/xilinx-dma.c | 6 ++-- drivers/media/usb/au0828/au0828-core.c | 4 +-- drivers/staging/media/imx/imx-media-utils.c | 6 ++-- drivers/staging/media/omap4iss/iss_video.c | 6 ++-- include/media/media-entity.h | 33 ++++++++++--------- 17 files changed, 76 insertions(+), 76 deletions(-) diff --git a/Documentation/media/kapi/mc-core.rst b/Documentation/media/kapi/mc-core.rst index 849b87439b7a9772..ede7e946f6a82ac0 100644 --- a/Documentation/media/kapi/mc-core.rst +++ b/Documentation/media/kapi/mc-core.rst @@ -211,11 +211,11 @@ When starting streaming, drivers must notify all entities in the pipeline to prevent link states from being modified during streaming by calling :c:func:`media_pipeline_start()`. -The function will mark all entities connected to the given entity through -enabled links, either directly or indirectly, as streaming. +The function will mark all entities connected to the given pad through +enabled routes and links, either directly or indirectly, as streaming. The struct :c:type:`media_pipeline` instance pointed to by -the pipe argument will be stored in every entity in the pipeline. +the pipe argument will be stored in every pad in the pipeline. Drivers should embed the struct :c:type:`media_pipeline` in higher-level pipeline structures and can then access the pipeline through the struct :c:type:`media_entity` diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 239036a7582cbc95..2722c38a822d7787 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -411,12 +411,11 @@ EXPORT_SYMBOL_GPL(media_entity_get_fwnode_pad); * Pipeline management */ -__must_check int __media_pipeline_start(struct media_entity *entity, +__must_check int __media_pipeline_start(struct media_pad *pad, struct media_pipeline *pipe) { - struct media_device *mdev = entity->graph_obj.mdev; + struct media_device *mdev = pad->graph_obj.mdev; struct media_graph *graph = &pipe->graph; - struct media_pad *pad = entity->pads; struct media_pad *pad_err = pad; struct media_link *link; int ret = 0; @@ -549,24 +548,23 @@ __must_check int __media_pipeline_start(struct media_entity *entity, } EXPORT_SYMBOL_GPL(__media_pipeline_start); -__must_check int media_pipeline_start(struct media_entity *entity, +__must_check int media_pipeline_start(struct media_pad *pad, struct media_pipeline *pipe) { - struct media_device *mdev = entity->graph_obj.mdev; + struct media_device *mdev = pad->graph_obj.mdev; int ret; mutex_lock(&mdev->graph_mutex); - ret = __media_pipeline_start(entity, pipe); + ret = __media_pipeline_start(pad, pipe); mutex_unlock(&mdev->graph_mutex); return ret; } EXPORT_SYMBOL_GPL(media_pipeline_start); -void __media_pipeline_stop(struct media_entity *entity) +void __media_pipeline_stop(struct media_pad *pad) { - struct media_pipeline *pipe = entity->pads->pipe; + struct media_pipeline *pipe = pad->pipe; struct media_graph *graph = &pipe->graph; - struct media_pad *pad; /* * If the following check fails, the driver has performed an @@ -575,9 +573,10 @@ void __media_pipeline_stop(struct media_entity *entity) if (WARN_ON(!pipe)) return; - media_graph_walk_start(graph, entity->pads); + media_graph_walk_start(graph, pad); while ((pad = media_graph_walk_next(graph))) { + struct media_entity *entity = pad->entity; unsigned int i; for (i = 0; i < entity->num_pads; i++) { @@ -598,12 +597,12 @@ void __media_pipeline_stop(struct media_entity *entity) } EXPORT_SYMBOL_GPL(__media_pipeline_stop); -void media_pipeline_stop(struct media_entity *entity) +void media_pipeline_stop(struct media_pad *pad) { - struct media_device *mdev = entity->graph_obj.mdev; + struct media_device *mdev = pad->graph_obj.mdev; mutex_lock(&mdev->graph_mutex); - __media_pipeline_stop(entity); + __media_pipeline_stop(pad); mutex_unlock(&mdev->graph_mutex); } EXPORT_SYMBOL_GPL(media_pipeline_stop); diff --git a/drivers/media/pci/intel/ipu3/ipu3-cio2.c b/drivers/media/pci/intel/ipu3/ipu3-cio2.c index 29027159eced88a5..7eb16e45c8069f4b 100644 --- a/drivers/media/pci/intel/ipu3/ipu3-cio2.c +++ b/drivers/media/pci/intel/ipu3/ipu3-cio2.c @@ -1002,7 +1002,7 @@ static int cio2_vb2_start_streaming(struct vb2_queue *vq, unsigned int count) return r; } - r = media_pipeline_start(&q->vdev.entity, &q->pipe); + r = media_pipeline_start(q->vdev.entity.pads, &q->pipe); if (r) goto fail_pipeline; @@ -1022,7 +1022,7 @@ static int cio2_vb2_start_streaming(struct vb2_queue *vq, unsigned int count) fail_csi2_subdev: cio2_hw_exit(cio2, q); fail_hw: - media_pipeline_stop(&q->vdev.entity); + media_pipeline_stop(q->vdev.entity.pads); fail_pipeline: dev_dbg(&cio2->pci_dev->dev, "failed to start streaming (%d)\n", r); cio2_vb2_return_all_buffers(q, VB2_BUF_STATE_QUEUED); @@ -1043,7 +1043,7 @@ static void cio2_vb2_stop_streaming(struct vb2_queue *vq) cio2_hw_exit(cio2, q); synchronize_irq(cio2->pci_dev->irq); cio2_vb2_return_all_buffers(q, VB2_BUF_STATE_ERROR); - media_pipeline_stop(&q->vdev.entity); + media_pipeline_stop(q->vdev.entity.pads); pm_runtime_put(&cio2->pci_dev->dev); cio2->streaming = false; } diff --git a/drivers/media/platform/exynos4-is/fimc-capture.c b/drivers/media/platform/exynos4-is/fimc-capture.c index a3cdac18819043df..88efbfbe8f61c0dc 100644 --- a/drivers/media/platform/exynos4-is/fimc-capture.c +++ b/drivers/media/platform/exynos4-is/fimc-capture.c @@ -537,7 +537,7 @@ static int fimc_capture_release(struct file *file) mutex_lock(&fimc->lock); if (close && vc->streaming) { - media_pipeline_stop(&vc->ve.vdev.entity); + media_pipeline_stop(vc->ve.vdev.entity.pads); vc->streaming = false; } @@ -1201,7 +1201,7 @@ static int fimc_cap_streamon(struct file *file, void *priv, if (fimc_capture_active(fimc)) return -EBUSY; - ret = media_pipeline_start(entity, &vc->ve.pipe->mp); + ret = media_pipeline_start(entity->pads, &vc->ve.pipe->mp); if (ret < 0) return ret; @@ -1235,7 +1235,7 @@ static int fimc_cap_streamon(struct file *file, void *priv, } err_p_stop: - media_pipeline_stop(entity); + media_pipeline_stop(entity->pads); return ret; } @@ -1250,7 +1250,7 @@ static int fimc_cap_streamoff(struct file *file, void *priv, if (ret < 0) return ret; - media_pipeline_stop(&vc->ve.vdev.entity); + media_pipeline_stop(vc->ve.vdev.entity.pads); vc->streaming = false; return 0; } diff --git a/drivers/media/platform/exynos4-is/fimc-isp-video.c b/drivers/media/platform/exynos4-is/fimc-isp-video.c index a920164f53f1f0ab..d0a40ab0b7e92362 100644 --- a/drivers/media/platform/exynos4-is/fimc-isp-video.c +++ b/drivers/media/platform/exynos4-is/fimc-isp-video.c @@ -312,7 +312,7 @@ static int isp_video_release(struct file *file) mutex_lock(&isp->video_lock); if (v4l2_fh_is_singular_file(file) && ivc->streaming) { - media_pipeline_stop(entity); + media_pipeline_stop(entity->pads); ivc->streaming = 0; } @@ -494,7 +494,7 @@ static int isp_video_streamon(struct file *file, void *priv, struct media_entity *me = &ve->vdev.entity; int ret; - ret = media_pipeline_start(me, &ve->pipe->mp); + ret = media_pipeline_start(me->pads, &ve->pipe->mp); if (ret < 0) return ret; @@ -509,7 +509,7 @@ static int isp_video_streamon(struct file *file, void *priv, isp->video_capture.streaming = 1; return 0; p_stop: - media_pipeline_stop(me); + media_pipeline_stop(me->pads); return ret; } @@ -524,7 +524,7 @@ static int isp_video_streamoff(struct file *file, void *priv, if (ret < 0) return ret; - media_pipeline_stop(&video->ve.vdev.entity); + media_pipeline_stop(video->ve.vdev.entity.pads); video->streaming = 0; return 0; } diff --git a/drivers/media/platform/exynos4-is/fimc-lite.c b/drivers/media/platform/exynos4-is/fimc-lite.c index f486eeed805b0bbc..e99a8c1a68541077 100644 --- a/drivers/media/platform/exynos4-is/fimc-lite.c +++ b/drivers/media/platform/exynos4-is/fimc-lite.c @@ -524,7 +524,7 @@ static int fimc_lite_release(struct file *file) if (v4l2_fh_is_singular_file(file) && atomic_read(&fimc->out_path) == FIMC_IO_DMA) { if (fimc->streaming) { - media_pipeline_stop(entity); + media_pipeline_stop(entity->pads); fimc->streaming = false; } fimc_lite_stop_capture(fimc, false); @@ -832,7 +832,7 @@ static int fimc_lite_streamon(struct file *file, void *priv, if (fimc_lite_active(fimc)) return -EBUSY; - ret = media_pipeline_start(entity, &fimc->ve.pipe->mp); + ret = media_pipeline_start(entity->pads, &fimc->ve.pipe->mp); if (ret < 0) return ret; @@ -849,7 +849,7 @@ static int fimc_lite_streamon(struct file *file, void *priv, } err_p_stop: - media_pipeline_stop(entity); + media_pipeline_stop(entity->pads); return 0; } @@ -863,7 +863,7 @@ static int fimc_lite_streamoff(struct file *file, void *priv, if (ret < 0) return ret; - media_pipeline_stop(&fimc->ve.vdev.entity); + media_pipeline_stop(fimc->ve.vdev.entity.pads); fimc->streaming = false; return 0; } diff --git a/drivers/media/platform/omap3isp/ispvideo.c b/drivers/media/platform/omap3isp/ispvideo.c index 5ac7ac8c98d52ac8..a9613c31a6b87e3c 100644 --- a/drivers/media/platform/omap3isp/ispvideo.c +++ b/drivers/media/platform/omap3isp/ispvideo.c @@ -1113,7 +1113,7 @@ isp_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) pipe->l3_ick = clk_get_rate(video->isp->clock[ISP_CLK_L3_ICK]); pipe->max_rate = pipe->l3_ick; - ret = media_pipeline_start(&video->video.entity, &pipe->pipe); + ret = media_pipeline_start(video->video.entity.pads, &pipe->pipe); if (ret < 0) goto err_pipeline_start; @@ -1170,7 +1170,7 @@ isp_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) return 0; err_check_format: - media_pipeline_stop(&video->video.entity); + media_pipeline_stop(video->video.entity.pads); err_pipeline_start: /* TODO: Implement PM QoS */ /* The DMA queue must be emptied here, otherwise CCDC interrupts that @@ -1237,7 +1237,7 @@ isp_video_streamoff(struct file *file, void *fh, enum v4l2_buf_type type) video->error = false; /* TODO: Implement PM QoS */ - media_pipeline_stop(&video->video.entity); + media_pipeline_stop(video->video.entity.pads); media_entity_enum_cleanup(&pipe->ent_enum); diff --git a/drivers/media/platform/qcom/camss/camss-video.c b/drivers/media/platform/qcom/camss/camss-video.c index c9bb0d023db480d1..8e828755c391ba48 100644 --- a/drivers/media/platform/qcom/camss/camss-video.c +++ b/drivers/media/platform/qcom/camss/camss-video.c @@ -436,7 +436,7 @@ static int video_start_streaming(struct vb2_queue *q, unsigned int count) struct v4l2_subdev *subdev; int ret; - ret = media_pipeline_start(&vdev->entity, &video->pipe); + ret = media_pipeline_start(vdev->entity.pads, &video->pipe); if (ret < 0) return ret; @@ -465,7 +465,7 @@ static int video_start_streaming(struct vb2_queue *q, unsigned int count) return 0; error: - media_pipeline_stop(&vdev->entity); + media_pipeline_stop(vdev->entity.pads); video->ops->flush_buffers(video, VB2_BUF_STATE_QUEUED); @@ -496,7 +496,7 @@ static void video_stop_streaming(struct vb2_queue *q) v4l2_subdev_call(subdev, video, s_stream, 0); } - media_pipeline_stop(&vdev->entity); + media_pipeline_stop(vdev->entity.pads); video->ops->flush_buffers(video, VB2_BUF_STATE_ERROR); } diff --git a/drivers/media/platform/rcar-vin/rcar-dma.c b/drivers/media/platform/rcar-vin/rcar-dma.c index e749096926f34d4a..57c2087f7ad472f3 100644 --- a/drivers/media/platform/rcar-vin/rcar-dma.c +++ b/drivers/media/platform/rcar-vin/rcar-dma.c @@ -1112,7 +1112,7 @@ static int rvin_set_stream(struct rvin_dev *vin, int on) sd = media_entity_to_v4l2_subdev(pad->entity); if (!on) { - media_pipeline_stop(&vin->vdev.entity); + media_pipeline_stop(vin->vdev.entity.pads); return v4l2_subdev_call(sd, video, s_stream, 0); } @@ -1129,7 +1129,7 @@ static int rvin_set_stream(struct rvin_dev *vin, int on) mdev = vin->vdev.entity.graph_obj.mdev; mutex_lock(&mdev->graph_mutex); pipe = sd->entity.pads->pipe ? sd->entity.pads->pipe : &vin->vdev.pipe; - ret = __media_pipeline_start(&vin->vdev.entity, pipe); + ret = __media_pipeline_start(vin->vdev.entity.pads, pipe); mutex_unlock(&mdev->graph_mutex); if (ret) return ret; @@ -1138,7 +1138,7 @@ static int rvin_set_stream(struct rvin_dev *vin, int on) if (ret == -ENOIOCTLCMD) ret = 0; if (ret) - media_pipeline_stop(&vin->vdev.entity); + media_pipeline_stop(vin->vdev.entity.pads); return ret; } diff --git a/drivers/media/platform/s3c-camif/camif-capture.c b/drivers/media/platform/s3c-camif/camif-capture.c index c02dce8b4c6c788b..3d7b92f0da33a5f9 100644 --- a/drivers/media/platform/s3c-camif/camif-capture.c +++ b/drivers/media/platform/s3c-camif/camif-capture.c @@ -858,13 +858,13 @@ static int s3c_camif_streamon(struct file *file, void *priv, if (s3c_vp_active(vp)) return 0; - ret = media_pipeline_start(sensor, camif->m_pipeline); + ret = media_pipeline_start(sensor->pads, camif->m_pipeline); if (ret < 0) return ret; ret = camif_pipeline_validate(camif); if (ret < 0) { - media_pipeline_stop(sensor); + media_pipeline_stop(sensor->pads); return ret; } @@ -888,7 +888,7 @@ static int s3c_camif_streamoff(struct file *file, void *priv, ret = vb2_streamoff(&vp->vb_queue, type); if (ret == 0) - media_pipeline_stop(&camif->sensor.sd->entity); + media_pipeline_stop(camif->sensor.sd->entity.pads); return ret; } diff --git a/drivers/media/platform/vimc/vimc-capture.c b/drivers/media/platform/vimc/vimc-capture.c index 88a1e5670c725101..de3fee15f0a73493 100644 --- a/drivers/media/platform/vimc/vimc-capture.c +++ b/drivers/media/platform/vimc/vimc-capture.c @@ -247,7 +247,7 @@ static int vimc_cap_start_streaming(struct vb2_queue *vq, unsigned int count) vcap->sequence = 0; /* Start the media pipeline */ - ret = media_pipeline_start(entity, &vcap->pipe); + ret = media_pipeline_start(entity->pads, &vcap->pipe); if (ret) { vimc_cap_return_all_buffers(vcap, VB2_BUF_STATE_QUEUED); return ret; @@ -256,7 +256,7 @@ static int vimc_cap_start_streaming(struct vb2_queue *vq, unsigned int count) /* Enable streaming from the pipe */ ret = vimc_pipeline_s_stream(&vcap->vdev.entity, 1); if (ret) { - media_pipeline_stop(entity); + media_pipeline_stop(entity->pads); vimc_cap_return_all_buffers(vcap, VB2_BUF_STATE_QUEUED); return ret; } @@ -276,7 +276,7 @@ static void vimc_cap_stop_streaming(struct vb2_queue *vq) vimc_pipeline_s_stream(&vcap->vdev.entity, 0); /* Stop the media pipeline */ - media_pipeline_stop(&vcap->vdev.entity); + media_pipeline_stop(vcap->vdev.entity.pads); /* Release all active buffers */ vimc_cap_return_all_buffers(vcap, VB2_BUF_STATE_ERROR); diff --git a/drivers/media/platform/vsp1/vsp1_video.c b/drivers/media/platform/vsp1/vsp1_video.c index f3e7f239e90c5f7d..241d2efbced27359 100644 --- a/drivers/media/platform/vsp1/vsp1_video.c +++ b/drivers/media/platform/vsp1/vsp1_video.c @@ -940,7 +940,7 @@ static void vsp1_video_stop_streaming(struct vb2_queue *vq) } mutex_unlock(&pipe->lock); - media_pipeline_stop(&video->video.entity); + media_pipeline_stop(video->video.entity.pads); vsp1_video_release_buffers(video); vsp1_video_pipeline_put(pipe); } @@ -1067,7 +1067,7 @@ vsp1_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) return PTR_ERR(pipe); } - ret = __media_pipeline_start(&video->video.entity, &pipe->pipe); + ret = __media_pipeline_start(video->video.entity.pads, &pipe->pipe); if (ret < 0) { mutex_unlock(&mdev->graph_mutex); goto err_pipe; @@ -1091,7 +1091,7 @@ vsp1_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) return 0; err_stop: - media_pipeline_stop(&video->video.entity); + media_pipeline_stop(video->video.entity.pads); err_pipe: vsp1_video_pipeline_put(pipe); return ret; diff --git a/drivers/media/platform/xilinx/xilinx-dma.c b/drivers/media/platform/xilinx/xilinx-dma.c index 9ea9a58eec632b7b..0fc948fe1a1aa0d8 100644 --- a/drivers/media/platform/xilinx/xilinx-dma.c +++ b/drivers/media/platform/xilinx/xilinx-dma.c @@ -409,7 +409,7 @@ static int xvip_dma_start_streaming(struct vb2_queue *vq, unsigned int count) pipe = dma->video.entity.pads->pipe ? to_xvip_pipeline(&dma->video.entity) : &dma->pipe; - ret = media_pipeline_start(&dma->video.entity, &pipe->pipe); + ret = media_pipeline_start(dma->video.entity.pads, &pipe->pipe); if (ret < 0) goto error; @@ -435,7 +435,7 @@ static int xvip_dma_start_streaming(struct vb2_queue *vq, unsigned int count) return 0; error_stop: - media_pipeline_stop(&dma->video.entity); + media_pipeline_stop(dma->video.entity.pads); error: /* Give back all queued buffers to videobuf2. */ @@ -463,7 +463,7 @@ static void xvip_dma_stop_streaming(struct vb2_queue *vq) /* Cleanup the pipeline and mark it as being stopped. */ xvip_pipeline_cleanup(pipe); - media_pipeline_stop(&dma->video.entity); + media_pipeline_stop(dma->video.entity.pads); /* Give back all queued buffers to videobuf2. */ spin_lock_irq(&dma->queued_lock); diff --git a/drivers/media/usb/au0828/au0828-core.c b/drivers/media/usb/au0828/au0828-core.c index cd363a2100d453c6..b649f11a45b586f2 100644 --- a/drivers/media/usb/au0828/au0828-core.c +++ b/drivers/media/usb/au0828/au0828-core.c @@ -394,7 +394,7 @@ static int au0828_enable_source(struct media_entity *entity, goto end; } - ret = __media_pipeline_start(entity, pipe); + ret = __media_pipeline_start(entity->pads, pipe); if (ret) { pr_err("Start Pipeline: %s->%s Error %d\n", source->name, entity->name, ret); @@ -445,7 +445,7 @@ static void au0828_disable_source(struct media_entity *entity) */ if (dev->active_link_owner != entity) return; - __media_pipeline_stop(entity); + __media_pipeline_stop(entity->pads); ret = __media_entity_setup_link(dev->active_link, 0); if (ret) pr_err("Deactivate link Error %d\n", ret); diff --git a/drivers/staging/media/imx/imx-media-utils.c b/drivers/staging/media/imx/imx-media-utils.c index 1cfa77a96e610f6c..b89e3f369d1b3686 100644 --- a/drivers/staging/media/imx/imx-media-utils.c +++ b/drivers/staging/media/imx/imx-media-utils.c @@ -909,16 +909,16 @@ int imx_media_pipeline_set_stream(struct imx_media_dev *imxmd, mutex_lock(&imxmd->md.graph_mutex); if (on) { - ret = __media_pipeline_start(entity, &imxmd->pipe); + ret = __media_pipeline_start(entity->pads, &imxmd->pipe); if (ret) goto out; ret = v4l2_subdev_call(sd, video, s_stream, 1); if (ret) - __media_pipeline_stop(entity); + __media_pipeline_stop(entity->pads); } else { v4l2_subdev_call(sd, video, s_stream, 0); if (entity->pads->pipe) - __media_pipeline_stop(entity); + __media_pipeline_stop(entity->pads); } out: diff --git a/drivers/staging/media/omap4iss/iss_video.c b/drivers/staging/media/omap4iss/iss_video.c index d1d91a79992a61bc..6ff6b75de4db80a1 100644 --- a/drivers/staging/media/omap4iss/iss_video.c +++ b/drivers/staging/media/omap4iss/iss_video.c @@ -898,7 +898,7 @@ iss_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) if (video->iss->pdata->set_constraints) video->iss->pdata->set_constraints(video->iss, true); - ret = media_pipeline_start(pad->entity, &pipe->pipe); + ret = media_pipeline_start(pad, &pipe->pipe); if (ret < 0) goto err_media_pipeline_start; @@ -987,7 +987,7 @@ iss_video_streamon(struct file *file, void *fh, enum v4l2_buf_type type) err_omap4iss_set_stream: vb2_streamoff(&vfh->queue, type); err_iss_video_check_format: - media_pipeline_stop(&video->video.entity); + media_pipeline_stop(video->video.entity.pads); err_media_pipeline_start: if (video->iss->pdata->set_constraints) video->iss->pdata->set_constraints(video->iss, false); @@ -1041,7 +1041,7 @@ iss_video_streamoff(struct file *file, void *fh, enum v4l2_buf_type type) if (video->iss->pdata->set_constraints) video->iss->pdata->set_constraints(video->iss, false); - media_pipeline_stop(&video->video.entity); + media_pipeline_stop(video->video.entity.pads); done: mutex_unlock(&video->stream_lock); diff --git a/include/media/media-entity.h b/include/media/media-entity.h index 4f68638153679a36..532c438b9eb862c5 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -917,53 +917,54 @@ struct media_pad *media_graph_walk_next(struct media_graph *graph); /** * media_pipeline_start - Mark a pipeline as streaming - * @entity: Starting entity - * @pipe: Media pipeline to be assigned to all entities in the pipeline. + * @pad: Starting pad + * @pipe: Media pipeline to be assigned to all pads in the pipeline. * - * Mark all entities connected to a given entity through enabled links, either - * directly or indirectly, as streaming. The given pipeline object is assigned - * to every entity in the pipeline and stored in the media_entity pipe field. + * Mark all pads connected to a given pad through enabled + * routes or links, either directly or indirectly, as streaming. The + * given pipeline object is assigned to every pad in the pipeline + * and stored in the media_pad pipe field. * * Calls to this function can be nested, in which case the same number of * media_pipeline_stop() calls will be required to stop streaming. The * pipeline pointer must be identical for all nested calls to * media_pipeline_start(). */ -__must_check int media_pipeline_start(struct media_entity *entity, +__must_check int media_pipeline_start(struct media_pad *pad, struct media_pipeline *pipe); /** * __media_pipeline_start - Mark a pipeline as streaming * - * @entity: Starting entity - * @pipe: Media pipeline to be assigned to all entities in the pipeline. + * @pad: Starting pad + * @pipe: Media pipeline to be assigned to all pads in the pipeline. * * ..note:: This is the non-locking version of media_pipeline_start() */ -__must_check int __media_pipeline_start(struct media_entity *entity, +__must_check int __media_pipeline_start(struct media_pad *pad, struct media_pipeline *pipe); /** * media_pipeline_stop - Mark a pipeline as not streaming - * @entity: Starting entity + * @pad: Starting pad * - * Mark all entities connected to a given entity through enabled links, either - * directly or indirectly, as not streaming. The media_entity pipe field is - * reset to %NULL. + * Mark all pads connected to a given pad through enabled routes or + * links, either directly or indirectly, as not streaming. The + * media_pad pipe field is reset to %NULL. * * If multiple calls to media_pipeline_start() have been made, the same * number of calls to this function are required to mark the pipeline as not * streaming. */ -void media_pipeline_stop(struct media_entity *entity); +void media_pipeline_stop(struct media_pad *pad); /** * __media_pipeline_stop - Mark a pipeline as not streaming * - * @entity: Starting entity + * @pad: Starting pad * * .. note:: This is the non-locking version of media_pipeline_stop() */ -void __media_pipeline_stop(struct media_entity *entity); +void __media_pipeline_stop(struct media_pad *pad); /** * media_devnode_create() - creates and initializes a device node interface From patchwork Thu Aug 23 13:25:21 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573847 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 396F51926 for ; Thu, 23 Aug 2018 13:28:10 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 329A02B72C for ; Thu, 23 Aug 2018 13:28:10 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 24AC12BDBF; Thu, 23 Aug 2018 13:28:10 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 274FE2BE0B for ; Thu, 23 Aug 2018 13:28:09 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730683AbeHWQ5u (ORCPT ); Thu, 23 Aug 2018 12:57:50 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12172 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730671AbeHWQ5u (ORCPT ); Thu, 23 Aug 2018 12:57:50 -0400 X-Halon-ID: 5e641bf0-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5e641bf0-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:06 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, Michal Simek Subject: [PATCH 07/30] media: entity: Add has_route entity operation Date: Thu, 23 Aug 2018 15:25:21 +0200 Message-Id: <20180823132544.521-8-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Laurent Pinchart The optional operation can be used by entities to report whether two pads are internally connected. Signed-off-by: Laurent Pinchart Signed-off-by: Michal Simek Signed-off-by: Sakari Ailus --- include/media/media-entity.h | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/include/media/media-entity.h b/include/media/media-entity.h index 532c438b9eb862c5..07df1b8d85a3c1ba 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -193,6 +193,9 @@ struct media_pad { * @link_validate: Return whether a link is valid from the entity point of * view. The media_pipeline_start() function * validates all links by calling this operation. Optional. + * @has_route: Return whether a route exists inside the entity between + * two given pads. Optional. If the operation isn't + * implemented all pads will be considered as connected. * * .. note:: * @@ -205,6 +208,8 @@ struct media_entity_operations { const struct media_pad *local, const struct media_pad *remote, u32 flags); int (*link_validate)(struct media_link *link); + bool (*has_route)(struct media_entity *entity, unsigned int pad0, + unsigned int pad1); }; /** From patchwork Thu Aug 23 13:25:22 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573851 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 1F14D1579 for ; Thu, 23 Aug 2018 13:28:11 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 1D6B12B72C for ; Thu, 23 Aug 2018 13:28:11 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 11CE42BDBF; Thu, 23 Aug 2018 13:28:11 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B838E2B736 for ; Thu, 23 Aug 2018 13:28:10 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730669AbeHWQ5v (ORCPT ); Thu, 23 Aug 2018 12:57:51 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12191 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730682AbeHWQ5u (ORCPT ); Thu, 23 Aug 2018 12:57:50 -0400 X-Halon-ID: 5ee0798d-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5ee0798d-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:07 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, Michal Simek Subject: [PATCH 08/30] media: entity: Add media_has_route() function Date: Thu, 23 Aug 2018 15:25:22 +0200 Message-Id: <20180823132544.521-9-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Laurent Pinchart This is a wrapper around the media entity has_route operation. Signed-off-by: Laurent Pinchart Signed-off-by: Michal Simek Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 16 ++++++++++++++++ include/media/media-entity.h | 17 +++++++++++++++++ 2 files changed, 33 insertions(+) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 2722c38a822d7787..2e5958732a9735cf 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -237,6 +237,22 @@ EXPORT_SYMBOL_GPL(media_entity_pads_init); * Graph traversal */ +bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, + unsigned int pad1) +{ + if (pad0 >= entity->num_pads || pad1 >= entity->num_pads) + return false; + + if (pad0 == pad1) + return true; + + if (!entity->ops || !entity->ops->has_route) + return true; + + return entity->ops->has_route(entity, pad0, pad1); +} +EXPORT_SYMBOL_GPL(media_entity_has_route); + static struct media_pad * media_entity_other(struct media_pad *pad, struct media_link *link) { diff --git a/include/media/media-entity.h b/include/media/media-entity.h index 07df1b8d85a3c1ba..53f293415fc39ab1 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -871,6 +871,23 @@ int media_entity_get_fwnode_pad(struct media_entity *entity, __must_check int media_graph_walk_init( struct media_graph *graph, struct media_device *mdev); +/** + * media_entity_has_route - Check if two entity pads are connected internally + * + * @entity: The entity + * @pad0: The first pad index + * @pad1: The second pad index + * + * This function can be used to check whether two pads of an entity are + * connected internally in the entity. + * + * The caller must hold entity->graph_obj.mdev->mutex. + * + * Return: true if the pads are connected internally and false otherwise. + */ +bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, + unsigned int pad1); + /** * media_graph_walk_cleanup - Release resources used by graph walk. * From patchwork Thu Aug 23 13:25:23 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573853 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 427C81926 for ; Thu, 23 Aug 2018 13:28:11 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 3A5F32B736 for ; Thu, 23 Aug 2018 13:28:11 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 2E71A2B72C; Thu, 23 Aug 2018 13:28:11 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id DCBA02BE0B for ; Thu, 23 Aug 2018 13:28:10 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730714AbeHWQ5w (ORCPT ); Thu, 23 Aug 2018 12:57:52 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12213 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730693AbeHWQ5v (ORCPT ); Thu, 23 Aug 2018 12:57:51 -0400 X-Halon-ID: 5f5e5b2b-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5f5e5b2b-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:08 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 09/30] media: entity: Swap pads if route is checked from source to sink Date: Thu, 23 Aug 2018 15:25:23 +0200 Message-Id: <20180823132544.521-10-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus This way the pads are always passed to the has_route() op sink pad first. Makes sense. Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 2e5958732a9735cf..88c8b838b78b39aa 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -249,6 +249,10 @@ bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, if (!entity->ops || !entity->ops->has_route) return true; + if (entity->pads[pad0].flags & MEDIA_PAD_FL_SOURCE + && entity->pads[pad1].flags & MEDIA_PAD_FL_SINK) + swap(pad0, pad1); + return entity->ops->has_route(entity, pad0, pad1); } EXPORT_SYMBOL_GPL(media_entity_has_route); From patchwork Thu Aug 23 13:25:24 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573939 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 1B9BA1579 for ; Thu, 23 Aug 2018 13:28:32 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 19A932B736 for ; Thu, 23 Aug 2018 13:28:32 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 0DF4A2BE0E; Thu, 23 Aug 2018 13:28:32 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id AB3982B737 for ; Thu, 23 Aug 2018 13:28:31 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730670AbeHWQ5w (ORCPT ); Thu, 23 Aug 2018 12:57:52 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12237 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730709AbeHWQ5w (ORCPT ); Thu, 23 Aug 2018 12:57:52 -0400 X-Halon-ID: 5fc93aec-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 5fc93aec-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:08 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, Michal Simek Subject: [PATCH 10/30] media: entity: Use routing information during graph traversal Date: Thu, 23 Aug 2018 15:25:24 +0200 Message-Id: <20180823132544.521-11-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Laurent Pinchart Take internal routing information as reported by the entity has_route operation into account during graph traversal to avoid following unrelated links. Signed-off-by: Laurent Pinchart Signed-off-by: Michal Simek Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 44 ++++++++++++++++++++++-------------- 1 file changed, 27 insertions(+), 17 deletions(-) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 88c8b838b78b39aa..12d9fc9ee02f38f2 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -257,15 +257,6 @@ bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, } EXPORT_SYMBOL_GPL(media_entity_has_route); -static struct media_pad * -media_entity_other(struct media_pad *pad, struct media_link *link) -{ - if (link->source == pad) - return link->sink; - else - return link->source; -} - /* push an entity to traversal stack */ static void stack_push(struct media_graph *graph, struct media_pad *pad) { @@ -336,7 +327,8 @@ static void media_graph_walk_iter(struct media_graph *graph) { struct media_pad *pad = stack_top(graph); struct media_link *link; - struct media_pad *next; + struct media_pad *remote; + struct media_pad *local; link = list_entry(link_top(graph), typeof(*link), list); @@ -350,23 +342,41 @@ static void media_graph_walk_iter(struct media_graph *graph) return; } - /* Get the entity in the other end of the link . */ - next = media_entity_other(pad, link); + /* + * Get the local pad, the remote pad and the entity at the other + * end of the link. + */ + if (link->source->entity == pad->entity) { + remote = link->sink; + local = link->source; + } else { + remote = link->source; + local = link->sink; + } + + /* + * Are the local pad and the pad we came from connected + * internally in the entity ? + */ + if (!media_entity_has_route(pad->entity, pad->index, local->index)) { + link_top(graph) = link_top(graph)->next; + return; + } /* Has the entity already been visited? */ - if (media_entity_enum_test_and_set(&graph->ent_enum, next->entity)) { + if (media_entity_enum_test_and_set(&graph->ent_enum, remote->entity)) { link_top(graph) = link_top(graph)->next; dev_dbg(pad->graph_obj.mdev->dev, "walk: skipping entity '%s' (already seen)\n", - next->entity->name); + remote->entity->name); return; } /* Push the new entity to stack and start over. */ link_top(graph) = link_top(graph)->next; - stack_push(graph, next); - dev_dbg(next->graph_obj.mdev->dev, "walk: pushing '%s':%u on stack\n", - next->entity->name, next->index); + stack_push(graph, remote); + dev_dbg(remote->graph_obj.mdev->dev, "walk: pushing '%s':%u on stack\n", + remote->entity->name, remote->index); } struct media_pad *media_graph_walk_next(struct media_graph *graph) From patchwork Thu Aug 23 13:25:25 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573935 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 4F894139B for ; Thu, 23 Aug 2018 13:28:31 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4B6DB2B736 for ; Thu, 23 Aug 2018 13:28:31 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 3FCD72BE0E; Thu, 23 Aug 2018 13:28:31 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id ECF762B736 for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728685AbeHWQ5x (ORCPT ); Thu, 23 Aug 2018 12:57:53 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12248 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730718AbeHWQ5x (ORCPT ); Thu, 23 Aug 2018 12:57:53 -0400 X-Halon-ID: 60467a0a-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 60467a0a-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:09 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 11/30] media: entity: Skip link validation for pads to which there is no route to Date: Thu, 23 Aug 2018 15:25:25 +0200 Message-Id: <20180823132544.521-12-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Links are validated along the pipeline which is about to start streaming. Not all the pads in entities that are traversed along that pipeline are part of the pipeline, however. Skip the link validation for such pads. Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 12d9fc9ee02f38f2..0395d58b2e233d88 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -493,6 +493,11 @@ __must_check int __media_pipeline_start(struct media_pad *pad, struct media_pad *other_pad = link->sink->entity == entity ? link->sink : link->source; + /* Ignore pads to which there is no route. */ + if (!media_entity_has_route(entity, pad->index, + other_pad->index)) + continue; + /* Mark that a pad is connected by a link. */ bitmap_clear(has_no_links, other_pad->index, 1); From patchwork Thu Aug 23 13:25:26 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573859 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id F3DFC13B6 for ; Thu, 23 Aug 2018 13:28:12 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id F03B22B736 for ; Thu, 23 Aug 2018 13:28:12 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id E486C2BE0B; Thu, 23 Aug 2018 13:28:12 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 95ABF2B736 for ; Thu, 23 Aug 2018 13:28:12 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730734AbeHWQ5x (ORCPT ); Thu, 23 Aug 2018 12:57:53 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12258 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730682AbeHWQ5x (ORCPT ); Thu, 23 Aug 2018 12:57:53 -0400 X-Halon-ID: 60a6a4f2-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 60a6a4f2-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:10 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 12/30] media: entity: Add an iterator helper for connected pads Date: Thu, 23 Aug 2018 15:25:26 +0200 Message-Id: <20180823132544.521-13-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Add a helper macro for iterating over pads that are connected through enabled routes. This can be used to find all the connected pads within an entity, for instance starting from the pad which has been obtained during the graph walk. Signed-off-by: Sakari Ailus --- include/media/media-entity.h | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/include/media/media-entity.h b/include/media/media-entity.h index 53f293415fc39ab1..169cf47982a0b1fa 100644 --- a/include/media/media-entity.h +++ b/include/media/media-entity.h @@ -888,6 +888,33 @@ __must_check int media_graph_walk_init( bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, unsigned int pad1); +static inline struct media_pad *__media_entity_for_routed_pads_next( + struct media_pad *start, struct media_pad *iter) +{ + struct media_entity *entity = start->entity; + + while (iter < &entity->pads[entity->num_pads] && + !media_entity_has_route(entity, start->index, iter->index)) + iter++; + + return iter; +} + +/** + * media_entity_for_routed_pads - Iterate over entity pads connected by routes + * + * @start: The stating pad + * @iter: The iterator pad + * + * Iterate over all pads connected through routes from a given pad + * within an entity. The iteration will include the starting pad itself. + */ +#define media_entity_for_routed_pads(start, iter) \ + for (iter = __media_entity_for_routed_pads_next( \ + start, (start)->entity->pads); \ + iter < &(start)->entity->pads[(start)->entity->num_pads]; \ + iter = __media_entity_for_routed_pads_next(start, iter + 1)) + /** * media_graph_walk_cleanup - Release resources used by graph walk. * From patchwork Thu Aug 23 13:25:27 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573931 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 8D75C139B for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 8C4342B737 for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 80FCB2BE23; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 38FA62B737 for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730764AbeHWQ5y (ORCPT ); Thu, 23 Aug 2018 12:57:54 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12279 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730718AbeHWQ5y (ORCPT ); Thu, 23 Aug 2018 12:57:54 -0400 X-Halon-ID: 6101598a-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6101598a-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:10 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 13/30] media: entity: Add only connected pads to the pipeline Date: Thu, 23 Aug 2018 15:25:27 +0200 Message-Id: <20180823132544.521-14-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus A single entity may contain multiple pipelines. Only add pads that were connected to the pad through which the entity was reached to the pipeline. Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 20 ++++++-------------- 1 file changed, 6 insertions(+), 14 deletions(-) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 0395d58b2e233d88..c11cf684b336f87e 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -460,15 +460,13 @@ __must_check int __media_pipeline_start(struct media_pad *pad, while ((pad = media_graph_walk_next(graph))) { struct media_entity *entity = pad->entity; - unsigned int i; + struct media_pad *iter; bool skip_validation = pad->pipe; DECLARE_BITMAP(active, MEDIA_ENTITY_MAX_PADS); DECLARE_BITMAP(has_no_links, MEDIA_ENTITY_MAX_PADS); - for (i = 0; i < entity->num_pads; i++) { - struct media_pad *iter = &entity->pads[i]; - + media_entity_for_routed_pads(pad, iter) { if (iter->pipe && WARN_ON(iter->pipe != pipe)) ret = -EBUSY; else @@ -553,12 +551,9 @@ __must_check int __media_pipeline_start(struct media_pad *pad, media_graph_walk_start(graph, pad_err); while ((pad_err = media_graph_walk_next(graph))) { - struct media_entity *entity_err = pad_err->entity; - unsigned int i; - - for (i = 0; i < entity_err->num_pads; i++) { - struct media_pad *iter = &entity_err->pads[i]; + struct media_pad *iter; + media_entity_for_routed_pads(pad_err, iter) { /* Sanity check for negative stream_count */ if (!WARN_ON_ONCE(iter->stream_count <= 0)) { --iter->stream_count; @@ -611,12 +606,9 @@ void __media_pipeline_stop(struct media_pad *pad) media_graph_walk_start(graph, pad); while ((pad = media_graph_walk_next(graph))) { - struct media_entity *entity = pad->entity; - unsigned int i; - - for (i = 0; i < entity->num_pads; i++) { - struct media_pad *iter = &entity->pads[i]; + struct media_pad *iter; + media_entity_for_routed_pads(pad, iter) { /* Sanity check for negative stream_count */ if (!WARN_ON_ONCE(iter->stream_count <= 0)) { iter->stream_count--; From patchwork Thu Aug 23 13:25:28 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573867 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id DE7BB1926 for ; Thu, 23 Aug 2018 13:28:14 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id DC33B2B72C for ; Thu, 23 Aug 2018 13:28:14 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id D0C912BDBF; Thu, 23 Aug 2018 13:28:14 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 93B752B72C for ; Thu, 23 Aug 2018 13:28:14 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730771AbeHWQ5z (ORCPT ); Thu, 23 Aug 2018 12:57:55 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12294 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730756AbeHWQ5y (ORCPT ); Thu, 23 Aug 2018 12:57:54 -0400 X-Halon-ID: 61642bac-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 61642bac-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:11 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 14/30] media: entity: Add debug information in graph walk route check Date: Thu, 23 Aug 2018 15:25:28 +0200 Message-Id: <20180823132544.521-15-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index c11cf684b336f87e..3912bc75651fe0b7 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -360,6 +360,9 @@ static void media_graph_walk_iter(struct media_graph *graph) */ if (!media_entity_has_route(pad->entity, pad->index, local->index)) { link_top(graph) = link_top(graph)->next; + dev_dbg(pad->graph_obj.mdev->dev, + "walk: skipping \"%s\":%u -> %u (no route)\n", + pad->entity->name, pad->index, local->index); return; } From patchwork Thu Aug 23 13:25:29 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573871 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id B24861579 for ; Thu, 23 Aug 2018 13:28:15 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id AF4192B72C for ; Thu, 23 Aug 2018 13:28:15 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id A3C8D2BDF5; Thu, 23 Aug 2018 13:28:15 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 5BF6E2B736 for ; Thu, 23 Aug 2018 13:28:15 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727666AbeHWQ54 (ORCPT ); Thu, 23 Aug 2018 12:57:56 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12317 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730682AbeHWQ5z (ORCPT ); Thu, 23 Aug 2018 12:57:55 -0400 X-Halon-ID: 61c61fb8-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 61c61fb8-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:12 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 15/30] media: entity: Look for indirect routes Date: Thu, 23 Aug 2018 15:25:29 +0200 Message-Id: <20180823132544.521-16-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Two pads are considered having an active route for the purpose of has_route() if an indirect active route can be found between the two pads. An simple example of this is that a source pad has an active route to another source pad if both of the pads have an active route to the same sink pad. Make media_entity_has_route() return true in that case, and do not rely on drivers performing this by themselves. Signed-off-by: Sakari Ailus --- drivers/media/media-entity.c | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) diff --git a/drivers/media/media-entity.c b/drivers/media/media-entity.c index 3912bc75651fe0b7..29e732a130667ae9 100644 --- a/drivers/media/media-entity.c +++ b/drivers/media/media-entity.c @@ -240,6 +240,9 @@ EXPORT_SYMBOL_GPL(media_entity_pads_init); bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, unsigned int pad1) { + unsigned int i; + bool has_route; + if (pad0 >= entity->num_pads || pad1 >= entity->num_pads) return false; @@ -253,7 +256,34 @@ bool media_entity_has_route(struct media_entity *entity, unsigned int pad0, && entity->pads[pad1].flags & MEDIA_PAD_FL_SINK) swap(pad0, pad1); - return entity->ops->has_route(entity, pad0, pad1); + has_route = entity->ops->has_route(entity, pad0, pad1); + /* A direct route is returned immediately */ + if (has_route || + (entity->pads[pad0].flags & MEDIA_PAD_FL_SINK && + entity->pads[pad1].flags & MEDIA_PAD_FL_SOURCE)) + return true; + + /* Look for indirect routes */ + for (i = 0; i < entity->num_pads; i++) { + if (i == pad0 || i == pad1) + continue; + + /* + * There are no direct routes between same types of + * pads, so skip checking this route + */ + if (!((entity->pads[pad0].flags ^ entity->pads[i].flags) & + (MEDIA_PAD_FL_SOURCE | MEDIA_PAD_FL_SINK))) + continue; + + /* Is there an indirect route? */ + if (entity->ops->has_route(entity, i, pad0) && + entity->ops->has_route(entity, i, pad1)) + return true; + } + + return false; + } EXPORT_SYMBOL_GPL(media_entity_has_route); From patchwork Thu Aug 23 13:25:30 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573875 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id D01DD1579 for ; Thu, 23 Aug 2018 13:28:16 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id CD5212B736 for ; Thu, 23 Aug 2018 13:28:16 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id C1A1C2BDBF; Thu, 23 Aug 2018 13:28:16 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4B9CA2B736 for ; Thu, 23 Aug 2018 13:28:16 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730788AbeHWQ54 (ORCPT ); Thu, 23 Aug 2018 12:57:56 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12338 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730748AbeHWQ54 (ORCPT ); Thu, 23 Aug 2018 12:57:56 -0400 X-Halon-ID: 6230de0e-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6230de0e-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:12 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, Michal Simek Subject: [PATCH 16/30] v4l: subdev: Add [GS]_ROUTING subdev ioctls and operations Date: Thu, 23 Aug 2018 15:25:30 +0200 Message-Id: <20180823132544.521-17-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Laurent Pinchart Signed-off-by: Laurent Pinchart Signed-off-by: Michal Simek - Add sink and source streams for multiplexed links - Copy the argument back in case of an error. This is needed to let the caller know the number of routes. Signed-off-by: Sakari Ailus --- drivers/media/v4l2-core/v4l2-ioctl.c | 20 +++++++++++++- drivers/media/v4l2-core/v4l2-subdev.c | 28 +++++++++++++++++++ include/media/v4l2-subdev.h | 7 +++++ include/uapi/linux/v4l2-subdev.h | 40 +++++++++++++++++++++++++++ 4 files changed, 94 insertions(+), 1 deletion(-) diff --git a/drivers/media/v4l2-core/v4l2-ioctl.c b/drivers/media/v4l2-core/v4l2-ioctl.c index 54afc9c7ee6ea162..68a0cf8b6f91208d 100644 --- a/drivers/media/v4l2-core/v4l2-ioctl.c +++ b/drivers/media/v4l2-core/v4l2-ioctl.c @@ -19,6 +19,7 @@ #include #include +#include #include #include @@ -2924,6 +2925,23 @@ static int check_array_args(unsigned int cmd, void *parg, size_t *array_size, } break; } + + case VIDIOC_SUBDEV_G_ROUTING: + case VIDIOC_SUBDEV_S_ROUTING: { + struct v4l2_subdev_routing *route = parg; + + if (route->num_routes > 0) { + if (route->num_routes > 256) + return -EINVAL; + + *user_ptr = (void __user *)route->routes; + *kernel_ptr = (void *)&route->routes; + *array_size = sizeof(struct v4l2_subdev_route) + * route->num_routes; + ret = 1; + } + break; + } } return ret; @@ -3033,7 +3051,7 @@ video_usercopy(struct file *file, unsigned int cmd, unsigned long arg, * Some ioctls can return an error, but still have valid * results that must be returned. */ - if (err < 0 && !always_copy) + if (err < 0 && !always_copy && cmd != VIDIOC_SUBDEV_G_ROUTING) goto out; out_array_args: diff --git a/drivers/media/v4l2-core/v4l2-subdev.c b/drivers/media/v4l2-core/v4l2-subdev.c index 2b63fa6b6fc9a739..601a2b23f736b382 100644 --- a/drivers/media/v4l2-core/v4l2-subdev.c +++ b/drivers/media/v4l2-core/v4l2-subdev.c @@ -516,7 +516,35 @@ static long subdev_do_ioctl(struct file *file, unsigned int cmd, void *arg) case VIDIOC_SUBDEV_QUERYSTD: return v4l2_subdev_call(sd, video, querystd, arg); + + case VIDIOC_SUBDEV_G_ROUTING: + return v4l2_subdev_call(sd, pad, get_routing, arg); + + case VIDIOC_SUBDEV_S_ROUTING: { + struct v4l2_subdev_routing *route = arg; + unsigned int i; + + if (route->num_routes > sd->entity.num_pads) + return -EINVAL; + + for (i = 0; i < route->num_routes; ++i) { + unsigned int sink = route->routes[i].sink_pad; + unsigned int source = route->routes[i].source_pad; + struct media_pad *pads = sd->entity.pads; + + if (sink >= sd->entity.num_pads || + source >= sd->entity.num_pads) + return -EINVAL; + + if (!(pads[sink].flags & MEDIA_PAD_FL_SINK) || + !(pads[source].flags & MEDIA_PAD_FL_SOURCE)) + return -EINVAL; + } + + return v4l2_subdev_call(sd, pad, set_routing, route); + } #endif + default: return v4l2_subdev_call(sd, core, ioctl, cmd, arg); } diff --git a/include/media/v4l2-subdev.h b/include/media/v4l2-subdev.h index 9102d6ca566e01f2..5acaeeb9b3cacefa 100644 --- a/include/media/v4l2-subdev.h +++ b/include/media/v4l2-subdev.h @@ -679,6 +679,9 @@ struct v4l2_subdev_pad_config { * * @set_frame_desc: set the low level media bus frame parameters, @fd array * may be adjusted by the subdev driver to device capabilities. + * + * @get_routing: callback for VIDIOC_SUBDEV_G_ROUTING IOCTL handler. + * @set_routing: callback for VIDIOC_SUBDEV_S_ROUTING IOCTL handler. */ struct v4l2_subdev_pad_ops { int (*init_cfg)(struct v4l2_subdev *sd, @@ -719,6 +722,10 @@ struct v4l2_subdev_pad_ops { struct v4l2_mbus_frame_desc *fd); int (*set_frame_desc)(struct v4l2_subdev *sd, unsigned int pad, struct v4l2_mbus_frame_desc *fd); + int (*get_routing)(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *route); + int (*set_routing)(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *route); }; /** diff --git a/include/uapi/linux/v4l2-subdev.h b/include/uapi/linux/v4l2-subdev.h index 03970ce3074193e6..af069bfb10ca23a5 100644 --- a/include/uapi/linux/v4l2-subdev.h +++ b/include/uapi/linux/v4l2-subdev.h @@ -155,6 +155,44 @@ struct v4l2_subdev_selection { __u32 reserved[8]; }; +#define V4L2_SUBDEV_ROUTE_FL_ACTIVE (1 << 0) +#define V4L2_SUBDEV_ROUTE_FL_IMMUTABLE (1 << 1) + +/** + * struct v4l2_subdev_route - A signal route inside a subdev + * @sink_pad: the sink pad + * @sink_stream: the sink stream + * @source_pad: the source pad + * @source_stream: the source stream + * @flags: route flags: + * + * V4L2_SUBDEV_ROUTE_FL_ACTIVE: Is the stream in use or not? An + * active stream will start when streaming is enabled on a video + * node. Set by the user. + * + * V4L2_SUBDEV_ROUTE_FL_IMMUTABLE: Is the stream immutable, i.e. + * can it be activated and inactivated? Set by the driver. + */ +struct v4l2_subdev_route { + __u32 sink_pad; + __u32 sink_stream; + __u32 source_pad; + __u32 source_stream; + __u32 flags; + __u32 reserved[5]; +}; + +/** + * struct v4l2_subdev_routing - Routing information + * @routes: the routes array + * @num_routes: the total number of routes in the routes array + */ +struct v4l2_subdev_routing { + struct v4l2_subdev_route *routes; + __u32 num_routes; + __u32 reserved[5]; +}; + /* Backwards compatibility define --- to be removed */ #define v4l2_subdev_edid v4l2_edid @@ -181,5 +219,7 @@ struct v4l2_subdev_selection { #define VIDIOC_SUBDEV_ENUM_DV_TIMINGS _IOWR('V', 98, struct v4l2_enum_dv_timings) #define VIDIOC_SUBDEV_QUERY_DV_TIMINGS _IOR('V', 99, struct v4l2_dv_timings) #define VIDIOC_SUBDEV_DV_TIMINGS_CAP _IOWR('V', 100, struct v4l2_dv_timings_cap) +#define VIDIOC_SUBDEV_G_ROUTING _IOWR('V', 38, struct v4l2_subdev_routing) +#define VIDIOC_SUBDEV_S_ROUTING _IOWR('V', 39, struct v4l2_subdev_routing) #endif From patchwork Thu Aug 23 13:25:31 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573879 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 472F613B6 for ; Thu, 23 Aug 2018 13:28:18 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 860D92B736 for ; Thu, 23 Aug 2018 13:28:17 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 7A5B52BE1C; Thu, 23 Aug 2018 13:28:17 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 1867C2B736 for ; Thu, 23 Aug 2018 13:28:17 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730802AbeHWQ55 (ORCPT ); Thu, 23 Aug 2018 12:57:57 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12359 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730785AbeHWQ55 (ORCPT ); Thu, 23 Aug 2018 12:57:57 -0400 X-Halon-ID: 62bd8901-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 62bd8901-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:13 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 17/30] v4l: subdev: compat: Implement handling for VIDIOC_SUBDEV_[GS]_ROUTING Date: Thu, 23 Aug 2018 15:25:31 +0200 Message-Id: <20180823132544.521-18-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Implement compat IOCTL handling for VIDIOC_SUBDEV_G_ROUTING and VIDIOC_SUBDEV_S_ROUTING IOCTLs. Signed-off-by: Sakari Ailus Signed-off-by: Niklas Söderlund --- drivers/media/v4l2-core/v4l2-compat-ioctl32.c | 75 +++++++++++++++++++ 1 file changed, 75 insertions(+) diff --git a/drivers/media/v4l2-core/v4l2-compat-ioctl32.c b/drivers/media/v4l2-core/v4l2-compat-ioctl32.c index 6481212fda772c73..b9112d6909ce0859 100644 --- a/drivers/media/v4l2-core/v4l2-compat-ioctl32.c +++ b/drivers/media/v4l2-core/v4l2-compat-ioctl32.c @@ -1045,6 +1045,64 @@ static int put_v4l2_event32(struct v4l2_event __user *p64, return 0; } +struct v4l2_subdev_routing32 { + compat_caddr_t routes; + __u32 num_routes; + __u32 reserved[5]; +}; + +static int get_v4l2_subdev_routing(struct v4l2_subdev_routing __user *kp, + struct v4l2_subdev_routing32 __user *up) +{ + struct v4l2_subdev_route __user *routes; + compat_caddr_t p; + u32 num_routes; + + if (!access_ok(VERIFY_READ, up, sizeof(*up)) || + get_user(p, &up->routes) || + get_user(num_routes, &up->num_routes) || + put_user(num_routes, &kp->num_routes) || + copy_in_user(&kp->reserved, &up->reserved, sizeof(kp->reserved)) || + num_routes > U32_MAX / sizeof(*kp->routes)) + return -EFAULT; + + routes = compat_ptr(p); + + if (!access_ok(VERIFY_READ, routes, + num_routes * sizeof(*kp->routes))) + return -EFAULT; + + if (put_user((__force struct v4l2_subdev_route *)routes, + &kp->routes)) + return -EFAULT; + + return 0; +} + +static int put_v4l2_subdev_routing(struct v4l2_subdev_routing __user *kp, + struct v4l2_subdev_routing32 __user *up) +{ + struct v4l2_subdev_route __user *routes; + compat_caddr_t p; + u32 num_routes; + + if (!access_ok(VERIFY_WRITE, up, sizeof(*up)) || + get_user(p, &up->routes) || + get_user(num_routes, &kp->num_routes) || + put_user(num_routes, &up->num_routes) || + copy_in_user(&up->reserved, &kp->reserved, sizeof(kp->reserved)) || + num_routes > U32_MAX / sizeof(*kp->routes)) + return -EFAULT; + + routes = compat_ptr(p); + + if (!access_ok(VERIFY_WRITE, routes, + num_routes * sizeof(*kp->routes))) + return -EFAULT; + + return 0; +} + struct v4l2_edid32 { __u32 pad; __u32 start_block; @@ -1117,6 +1175,8 @@ static int put_v4l2_edid32(struct v4l2_edid __user *p64, #define VIDIOC_STREAMOFF32 _IOW ('V', 19, s32) #define VIDIOC_G_INPUT32 _IOR ('V', 38, s32) #define VIDIOC_S_INPUT32 _IOWR('V', 39, s32) +#define VIDIOC_SUBDEV_G_ROUTING32 _IOWR('V', 38, struct v4l2_subdev_routing32) +#define VIDIOC_SUBDEV_S_ROUTING32 _IOWR('V', 39, struct v4l2_subdev_routing32) #define VIDIOC_G_OUTPUT32 _IOR ('V', 46, s32) #define VIDIOC_S_OUTPUT32 _IOWR('V', 47, s32) @@ -1195,6 +1255,8 @@ static long do_video_ioctl(struct file *file, unsigned int cmd, unsigned long ar case VIDIOC_STREAMOFF32: cmd = VIDIOC_STREAMOFF; break; case VIDIOC_G_INPUT32: cmd = VIDIOC_G_INPUT; break; case VIDIOC_S_INPUT32: cmd = VIDIOC_S_INPUT; break; + case VIDIOC_SUBDEV_G_ROUTING32: cmd = VIDIOC_SUBDEV_G_ROUTING; break; + case VIDIOC_SUBDEV_S_ROUTING32: cmd = VIDIOC_SUBDEV_S_ROUTING; break; case VIDIOC_G_OUTPUT32: cmd = VIDIOC_G_OUTPUT; break; case VIDIOC_S_OUTPUT32: cmd = VIDIOC_S_OUTPUT; break; case VIDIOC_CREATE_BUFS32: cmd = VIDIOC_CREATE_BUFS; break; @@ -1227,6 +1289,15 @@ static long do_video_ioctl(struct file *file, unsigned int cmd, unsigned long ar compatible_arg = 0; break; + case VIDIOC_SUBDEV_G_ROUTING: + case VIDIOC_SUBDEV_S_ROUTING: + err = alloc_userspace(sizeof(struct v4l2_subdev_routing), + 0, &new_p64); + if (!err) + err = get_v4l2_subdev_routing(new_p64, p32); + compatible_arg = 0; + break; + case VIDIOC_G_EDID: case VIDIOC_S_EDID: err = alloc_userspace(sizeof(struct v4l2_edid), 0, &new_p64); @@ -1368,6 +1439,10 @@ static long do_video_ioctl(struct file *file, unsigned int cmd, unsigned long ar if (put_v4l2_edid32(new_p64, p32)) err = -EFAULT; break; + case VIDIOC_SUBDEV_G_ROUTING: + case VIDIOC_SUBDEV_S_ROUTING: + err = put_v4l2_subdev_routing(new_p64, p32); + break; } if (err) return err; From patchwork Thu Aug 23 13:25:32 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573933 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id AE5661579 for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A8F0D2B736 for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 9CEE92BE23; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 0D03A2B736 for ; Thu, 23 Aug 2018 13:28:30 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730822AbeHWQ56 (ORCPT ); Thu, 23 Aug 2018 12:57:58 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12377 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730783AbeHWQ56 (ORCPT ); Thu, 23 Aug 2018 12:57:58 -0400 X-Halon-ID: 633b062f-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 633b062f-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:14 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 18/30] v4l: subdev: Take routing information into account in link validation Date: Thu, 23 Aug 2018 15:25:32 +0200 Message-Id: <20180823132544.521-19-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus The routing information is essential in link validation for multiplexed links: the pads at the ends of a multiplexed link have no single format defined for them. Instead, the format is accessible in the sink (or source) pads of the sub-devices at both ends of that link. Signed-off-by: Sakari Ailus --- drivers/media/v4l2-core/v4l2-subdev.c | 217 ++++++++++++++++++++++++-- 1 file changed, 203 insertions(+), 14 deletions(-) diff --git a/drivers/media/v4l2-core/v4l2-subdev.c b/drivers/media/v4l2-core/v4l2-subdev.c index 601a2b23f736b382..1f480ff6c29b4c0c 100644 --- a/drivers/media/v4l2-core/v4l2-subdev.c +++ b/drivers/media/v4l2-core/v4l2-subdev.c @@ -640,12 +640,17 @@ static int v4l2_subdev_link_validate_get_format(struct media_pad *pad, struct v4l2_subdev_format *fmt) { + dev_dbg(pad->entity->graph_obj.mdev->dev, + "obtaining format on \"%s\":%u\n", pad->entity->name, + pad->index); + if (is_media_entity_v4l2_subdev(pad->entity)) { struct v4l2_subdev *sd = media_entity_to_v4l2_subdev(pad->entity); fmt->which = V4L2_SUBDEV_FORMAT_ACTIVE; fmt->pad = pad->index; + return v4l2_subdev_call(sd, pad, get_fmt, NULL, fmt); } @@ -656,31 +661,215 @@ v4l2_subdev_link_validate_get_format(struct media_pad *pad, return -EINVAL; } -int v4l2_subdev_link_validate(struct media_link *link) +static int v4l2_subdev_link_validate_one(struct media_link *link, + struct v4l2_subdev_format *source_fmt, + struct v4l2_subdev_format *sink_fmt) { struct v4l2_subdev *sink; - struct v4l2_subdev_format sink_fmt, source_fmt; int rval; - rval = v4l2_subdev_link_validate_get_format( - link->source, &source_fmt); - if (rval < 0) - return 0; - - rval = v4l2_subdev_link_validate_get_format( - link->sink, &sink_fmt); - if (rval < 0) - return 0; - sink = media_entity_to_v4l2_subdev(link->sink->entity); rval = v4l2_subdev_call(sink, pad, link_validate, link, - &source_fmt, &sink_fmt); + source_fmt, sink_fmt); if (rval != -ENOIOCTLCMD) return rval; return v4l2_subdev_link_validate_default( - sink, link, &source_fmt, &sink_fmt); + sink, link, source_fmt, sink_fmt); +} + +/* How many routes to assume there can be per a sub-device? */ +#define LINK_VALIDATE_ROUTES 8 + +#define R_SRC 0 +#define R_SINK 1 +#define NR_R 2 + +int v4l2_subdev_link_validate(struct media_link *link) +{ + struct v4l2_subdev *sink; + struct route_info { + struct v4l2_subdev_route routes[LINK_VALIDATE_ROUTES]; + struct v4l2_subdev_routing routing; + bool has_route; + struct media_pad *pad; + /* Format for a non-multiplexed pad. */ + struct v4l2_subdev_format fmt; + } r[NR_R] = { + { + /* Source end of the link */ + .routing = { + .routes = r[R_SRC].routes, + .num_routes = ARRAY_SIZE(r[R_SRC].routes), + }, + .pad = link->source, + }, + { + /* Sink end of the link */ + .routing = { + .routes = r[R_SINK].routes, + .num_routes = ARRAY_SIZE(r[R_SINK].routes), + }, + .pad = link->sink, + }, + }; + unsigned int i, j; + int rval; + + sink = media_entity_to_v4l2_subdev(link->sink->entity); + + dev_dbg(sink->entity.graph_obj.mdev->dev, + "validating link \"%s\":%u -> \"%s\":%u\n", + link->source->entity->name, link->source->index, + sink->entity.name, link->sink->index); + + for (i = 0; i < NR_R; i++) { + struct route_info *ri = &r[i]; + + ri->has_route = true; + + rval = v4l2_subdev_call( + media_entity_to_v4l2_subdev(ri->pad->entity), + pad, get_routing, &ri->routing); + + switch (rval) { + case 0: + break; + case -ENOIOCTLCMD: + dev_dbg(sink->entity.graph_obj.mdev->dev, + "no routing information on \"%s\":%u\n", + ri->pad->entity->name, ri->pad->index); + ri->has_route = false; + break; + default: + dev_dbg(sink->entity.graph_obj.mdev->dev, + "error %d in get_routing() on \"%s\":%u\n", + rval, ri->pad->entity->name, ri->pad->index); + return rval; + } + + rval = v4l2_subdev_link_validate_get_format(ri->pad, + &ri->fmt); + + if (!rval) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "format information available on \"%s\":%u\n", + ri->pad->entity->name, ri->pad->index); + ri->has_route = false; + } + + if (!ri->has_route) { + ri->routing.num_routes = 1; + } else { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "routes on \"%s\":%u:\n", + ri->pad->entity->name, ri->pad->index); + for (j = 0; j < ri->routing.num_routes; j++) + dev_dbg(sink->entity.graph_obj.mdev->dev, + "\t%u: %u/%u -> %u/%u\n", j, + ri->routing.routes[j].sink_pad, + ri->routing.routes[j].sink_stream, + ri->routing.routes[j].source_pad, + ri->routing.routes[j].source_stream); + } + } + + for (i = 0, j = 0; + i < r[R_SRC].routing.num_routes && + j < r[R_SINK].routing.num_routes; ) { + unsigned int *ro[] = { &i, &j }; + unsigned int k; + + /* Get the first active route for the sink pad. */ + if (r[R_SINK].has_route && + (r[R_SINK].routes[j].sink_pad != link->sink->index || + !(r[R_SINK].routes[j].flags + & V4L2_SUBDEV_ROUTE_FL_ACTIVE))) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "skipping route %u/%u -> %u/%u[%u]\n", + r[R_SINK].routes[j].sink_pad, + r[R_SINK].routes[j].sink_stream, + r[R_SINK].routes[j].source_pad, + r[R_SINK].routes[j].source_stream, + (bool)(r[R_SINK].routes[j].flags + & V4L2_SUBDEV_ROUTE_FL_ACTIVE)); + j++; + continue; + } + + /* + * Get the corresponding route for the source pad. + * It's ok for the source pad to have routes active + * where the sink pad does not, but the routes that + * are active on the sink pad have to be active on + * the source pad as well. + */ + if (r[R_SRC].has_route && + (r[R_SRC].routes[i].source_pad != link->source->index || + r[R_SRC].routes[i].source_stream + != r[R_SINK].routes[j].sink_stream)) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "skipping source route %u/%u -> %u/%u\n", + r[R_SRC].routes[i].sink_pad, + r[R_SRC].routes[i].sink_stream, + r[R_SRC].routes[i].source_pad, + r[R_SRC].routes[i].source_stream); + i++; + continue; + } + + /* The source route must be active. */ + if (r[R_SRC].has_route && + !(r[R_SRC].routes[i].flags + & V4L2_SUBDEV_ROUTE_FL_ACTIVE)) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "source route not active\n"); + return -EINVAL; + } + + for (k = 0; k < NR_R; k++) { + if (r[k].has_route) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "validating %s route \"%s\": %u/%u -> %u/%u\n", + k == R_SINK ? "sink" : "source", + r[k].pad->entity->name, + r[k].routes[*ro[k]].sink_pad, + r[k].routes[*ro[k]].sink_stream, + r[k].routes[*ro[k]].source_pad, + r[k].routes[*ro[k]].source_stream); + rval = v4l2_subdev_link_validate_get_format( + &r[k].pad->entity->pads[ + k == R_SINK + ? r[k].routes[*ro[k]].source_pad + : r[k].routes[*ro[k]].sink_pad], + &r[k].fmt); + } else { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "routing not supported by \"%s\":%u", + r[k].pad->entity->name, + r[k].pad->index); + } + } + + rval = v4l2_subdev_link_validate_one( + link, &r[R_SRC].fmt, &r[R_SINK].fmt); + if (rval) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "error %d in link validation\n", rval); + return rval; + } + + i++, j++; + } + + if (j < r[R_SINK].routing.num_routes) { + dev_dbg(sink->entity.graph_obj.mdev->dev, + "not all sink routes verified; out of source routes\n"); + return -EINVAL; + } + + return 0; } EXPORT_SYMBOL_GPL(v4l2_subdev_link_validate); From patchwork Thu Aug 23 13:25:33 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573885 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 6E2D71926 for ; Thu, 23 Aug 2018 13:28:20 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 0946B2B72C for ; Thu, 23 Aug 2018 13:28:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id F1ACC2BE23; Thu, 23 Aug 2018 13:28:19 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 981A22BE1C for ; Thu, 23 Aug 2018 13:28:19 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730835AbeHWQ57 (ORCPT ); Thu, 23 Aug 2018 12:57:59 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12399 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730821AbeHWQ56 (ORCPT ); Thu, 23 Aug 2018 12:57:58 -0400 X-Halon-ID: 63bcd9f7-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 63bcd9f7-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:15 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 19/30] v4l: subdev: Improve link format validation debug messages Date: Thu, 23 Aug 2018 15:25:33 +0200 Message-Id: <20180823132544.521-20-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus The existing link format validation failure debug message in media-entity.c helped to poinpoint the point of failure but provided no additional information what's wrong. Tell the user exactly why the validation failed. Signed-off-by: Sakari Ailus --- drivers/media/v4l2-core/v4l2-subdev.c | 40 ++++++++++++++++++++++----- 1 file changed, 33 insertions(+), 7 deletions(-) diff --git a/drivers/media/v4l2-core/v4l2-subdev.c b/drivers/media/v4l2-core/v4l2-subdev.c index 1f480ff6c29b4c0c..31f67daeadc1eaf2 100644 --- a/drivers/media/v4l2-core/v4l2-subdev.c +++ b/drivers/media/v4l2-core/v4l2-subdev.c @@ -618,21 +618,47 @@ int v4l2_subdev_link_validate_default(struct v4l2_subdev *sd, struct v4l2_subdev_format *source_fmt, struct v4l2_subdev_format *sink_fmt) { + bool pass = true; + /* The width, height and code must match. */ - if (source_fmt->format.width != sink_fmt->format.width - || source_fmt->format.height != sink_fmt->format.height - || source_fmt->format.code != sink_fmt->format.code) - return -EPIPE; + if (source_fmt->format.width != sink_fmt->format.width) { + dev_dbg(sd->entity.graph_obj.mdev->dev, + "%s: width does not match (source %u, sink %u)\n", + __func__, + source_fmt->format.width, sink_fmt->format.width); + pass = false; + } + + if (source_fmt->format.height != sink_fmt->format.height) { + dev_dbg(sd->entity.graph_obj.mdev->dev, + "%s: height does not match (source %u, sink %u)\n", + __func__, + source_fmt->format.height, sink_fmt->format.height); + pass = false; + } + + if (source_fmt->format.code != sink_fmt->format.code) { + dev_dbg(sd->entity.graph_obj.mdev->dev, + "%s: media bus code does not match (source 0x%8.8x, sink 0x%8.8x)\n", + __func__, + source_fmt->format.code, sink_fmt->format.code); + pass = false; + } /* The field order must match, or the sink field order must be NONE * to support interlaced hardware connected to bridges that support * progressive formats only. */ if (source_fmt->format.field != sink_fmt->format.field && - sink_fmt->format.field != V4L2_FIELD_NONE) - return -EPIPE; + sink_fmt->format.field != V4L2_FIELD_NONE) { + dev_dbg(sd->entity.graph_obj.mdev->dev, + "%s: field does not match (source %u, sink %u)\n", + __func__, + source_fmt->format.field, sink_fmt->format.field); + pass = false; + } - return 0; + return pass ? 0 : -EPIPE; } EXPORT_SYMBOL_GPL(v4l2_subdev_link_validate_default); From patchwork Thu Aug 23 13:25:34 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573887 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 96CE513B6 for ; Thu, 23 Aug 2018 13:28:20 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 693612BE1C for ; Thu, 23 Aug 2018 13:28:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 5D95B2BE23; Thu, 23 Aug 2018 13:28:20 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4CEC42BE0E for ; Thu, 23 Aug 2018 13:28:19 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730844AbeHWQ6A (ORCPT ); Thu, 23 Aug 2018 12:58:00 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12409 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730794AbeHWQ57 (ORCPT ); Thu, 23 Aug 2018 12:57:59 -0400 X-Halon-ID: 642575ef-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 642575ef-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:16 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 20/30] v4l: mc: Add an S_ROUTING helper function for power state changes Date: Thu, 23 Aug 2018 15:25:34 +0200 Message-Id: <20180823132544.521-21-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus With the addition of the has_route() media entity operation, all pads of an entity are no longer interconnected. The S_ROUTING IOCTL for sub-devices can be used to enable and disable routes for an entity. The consequence is that the routing information has to be taken into account in use count calculation: disabling a route has a very similar effect on use counts as has disabling a link. Add a helper function for drivers implementing VIDIOC_SUBDEV_S_ROUTING IOCTL to take the change into account. Signed-off-by: Sakari Ailus --- drivers/media/v4l2-core/v4l2-mc.c | 34 +++++++++++++++++++++++++++++++ include/media/v4l2-mc.h | 22 ++++++++++++++++++++ 2 files changed, 56 insertions(+) diff --git a/drivers/media/v4l2-core/v4l2-mc.c b/drivers/media/v4l2-core/v4l2-mc.c index f702cac5205b3447..2ca4b0d62dd943ff 100644 --- a/drivers/media/v4l2-core/v4l2-mc.c +++ b/drivers/media/v4l2-core/v4l2-mc.c @@ -401,3 +401,37 @@ int v4l2_pipeline_link_notify(struct media_link *link, u32 flags, return ret; } EXPORT_SYMBOL_GPL(v4l2_pipeline_link_notify); + +int v4l2_subdev_routing_pm_use(struct media_entity *entity, + struct v4l2_subdev_route *route) +{ + struct media_graph *graph = + &entity->graph_obj.mdev->pm_count_walk; + struct media_pad *source = &entity->pads[route->source_pad]; + struct media_pad *sink = &entity->pads[route->sink_pad]; + int source_use; + int sink_use; + int ret; + + source_use = pipeline_pm_use_count(source, graph); + sink_use = pipeline_pm_use_count(sink, graph); + + if (!(route->flags & V4L2_SUBDEV_ROUTE_FL_ACTIVE)) { + /* Route disabled. */ + pipeline_pm_power(source, -sink_use, graph); + pipeline_pm_power(sink, -source_use, graph); + return 0; + } + + /* Route enabled. */ + ret = pipeline_pm_power(source, sink_use, graph); + if (ret < 0) + return ret; + + ret = pipeline_pm_power(sink, source_use, graph); + if (ret < 0) + pipeline_pm_power(source, -sink_use, graph); + + return ret; +} +EXPORT_SYMBOL_GPL(v4l2_subdev_routing_pm_use); diff --git a/include/media/v4l2-mc.h b/include/media/v4l2-mc.h index 2634d9dc9916e3c4..ea0a54bd951f5330 100644 --- a/include/media/v4l2-mc.h +++ b/include/media/v4l2-mc.h @@ -104,6 +104,7 @@ enum demod_pad_index { /* We don't need to include pci.h or usb.h here */ struct pci_dev; struct usb_device; +struct v4l2_subdev_route; #ifdef CONFIG_MEDIA_CONTROLLER /** @@ -210,6 +211,22 @@ int v4l2_pipeline_pm_use(struct media_entity *entity, int use); int v4l2_pipeline_link_notify(struct media_link *link, u32 flags, unsigned int notification); +/** + * v4l2_subdev_routing_pm_use - Handle power state changes due to S_ROUTING + * @entity: The entity + * @route: The new state of the route + * + * Propagate the use count across a route in a pipeline whenever the + * route is enabled or disabled. The function is called before + * changing the route state when enabling a route, and after changing + * the route state when disabling a route. + * + * Return 0 on success or a negative error code on failure. Powering entities + * off is assumed to never fail. This function will not fail for disconnection + * events. + */ +int v4l2_subdev_routing_pm_use(struct media_entity *entity, + struct v4l2_subdev_route *route); #else /* CONFIG_MEDIA_CONTROLLER */ static inline int v4l2_mc_create_media_graph(struct media_device *mdev) @@ -242,5 +259,10 @@ static inline int v4l2_pipeline_link_notify(struct media_link *link, u32 flags, return 0; } +static inline int v4l2_subdev_routing_pm_use(struct media_entity *entity, + struct v4l2_subdev_route *route) +{ + return 0; +} #endif /* CONFIG_MEDIA_CONTROLLER */ #endif /* _V4L2_MC_H */ From patchwork Thu Aug 23 13:25:35 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573927 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id D791A13B6 for ; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id D5E6B2BE0E for ; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id C85732BE23; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 6B50D2B736 for ; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730862AbeHWQ6B (ORCPT ); Thu, 23 Aug 2018 12:58:01 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12430 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730718AbeHWQ6A (ORCPT ); Thu, 23 Aug 2018 12:58:00 -0400 X-Halon-ID: 648f48d3-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 648f48d3-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:16 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 21/30] v4l: Add bus type to frame descriptors Date: Thu, 23 Aug 2018 15:25:35 +0200 Message-Id: <20180823132544.521-22-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Signed-off-by: Sakari Ailus Reviewed-by: Kieran Bingham --- include/media/v4l2-subdev.h | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/include/media/v4l2-subdev.h b/include/media/v4l2-subdev.h index 5acaeeb9b3cacefa..ac1f7ee4cdb978ad 100644 --- a/include/media/v4l2-subdev.h +++ b/include/media/v4l2-subdev.h @@ -349,12 +349,21 @@ struct v4l2_mbus_frame_desc_entry { #define V4L2_FRAME_DESC_ENTRY_MAX 4 +enum { + V4L2_MBUS_FRAME_DESC_TYPE_PLATFORM, + V4L2_MBUS_FRAME_DESC_TYPE_PARALLEL, + V4L2_MBUS_FRAME_DESC_TYPE_CCP2, + V4L2_MBUS_FRAME_DESC_TYPE_CSI2, +}; + /** * struct v4l2_mbus_frame_desc - media bus data frame description + * @type: type of the bus (V4L2_MBUS_FRAME_DESC_TYPE_*) * @entry: frame descriptors array * @num_entries: number of entries in @entry array */ struct v4l2_mbus_frame_desc { + u32 type; struct v4l2_mbus_frame_desc_entry entry[V4L2_FRAME_DESC_ENTRY_MAX]; unsigned short num_entries; }; From patchwork Thu Aug 23 13:25:36 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573893 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id E40C2139B for ; Thu, 23 Aug 2018 13:28:21 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 39DE12B72C for ; Thu, 23 Aug 2018 13:28:21 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 2E7332BE0E; Thu, 23 Aug 2018 13:28:21 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id D85D92BE23 for ; Thu, 23 Aug 2018 13:28:20 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730896AbeHWQ6C (ORCPT ); Thu, 23 Aug 2018 12:58:02 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12452 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730851AbeHWQ6B (ORCPT ); Thu, 23 Aug 2018 12:58:01 -0400 X-Halon-ID: 6527a199-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6527a199-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:17 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 22/30] v4l: Add CSI-2 bus configuration to frame descriptors Date: Thu, 23 Aug 2018 15:25:36 +0200 Message-Id: <20180823132544.521-23-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus Add CSI-2 bus specific configuration to the frame descriptors. This allows obtaining the virtual channel and data type information for each stream the transmitter is sending. Signed-off-by: Sakari Ailus --- include/media/v4l2-subdev.h | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/include/media/v4l2-subdev.h b/include/media/v4l2-subdev.h index ac1f7ee4cdb978ad..ffd98e4f368358a6 100644 --- a/include/media/v4l2-subdev.h +++ b/include/media/v4l2-subdev.h @@ -317,6 +317,17 @@ struct v4l2_subdev_audio_ops { int (*s_stream)(struct v4l2_subdev *sd, int enable); }; +/** + * struct v4l2_mbus_frame_desc_entry_csi2 + * + * @channel: CSI-2 virtual channel + * @data_type: CSI-2 data type ID + */ +struct v4l2_mbus_frame_desc_entry_csi2 { + u8 channel; + u8 data_type; +}; + /** * enum v4l2_mbus_frame_desc_entry - media bus frame description flags * @@ -340,11 +351,16 @@ enum v4l2_mbus_frame_desc_flags { * %FRAME_DESC_FL_BLOB is not set. * @length: number of octets per frame, valid if @flags * %V4L2_MBUS_FRAME_DESC_FL_LEN_MAX is set. + * @bus: Bus specific frame descriptor parameters + * @bus.csi2: CSI-2 specific bus configuration */ struct v4l2_mbus_frame_desc_entry { enum v4l2_mbus_frame_desc_flags flags; u32 pixelcode; u32 length; + union { + struct v4l2_mbus_frame_desc_entry_csi2 csi2; + } bus; }; #define V4L2_FRAME_DESC_ENTRY_MAX 4 From patchwork Thu Aug 23 13:25:37 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573929 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id EC1321579 for ; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id E9CCA2B736 for ; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id D63A02C0FF; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 961572B737 for ; Thu, 23 Aug 2018 13:28:29 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731113AbeHWQ6L (ORCPT ); Thu, 23 Aug 2018 12:58:11 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12470 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730892AbeHWQ6C (ORCPT ); Thu, 23 Aug 2018 12:58:02 -0400 X-Halon-ID: 658b112e-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 658b112e-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:18 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org Subject: [PATCH 23/30] v4l: Add stream to frame descriptor Date: Thu, 23 Aug 2018 15:25:37 +0200 Message-Id: <20180823132544.521-24-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Sakari Ailus The stream field identifies the stream this frame descriptor applies to in routing configuration across a multiplexed link. Signed-off-by: Sakari Ailus --- include/media/v4l2-subdev.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/media/v4l2-subdev.h b/include/media/v4l2-subdev.h index ffd98e4f368358a6..5fbce1932107a990 100644 --- a/include/media/v4l2-subdev.h +++ b/include/media/v4l2-subdev.h @@ -347,6 +347,7 @@ enum v4l2_mbus_frame_desc_flags { * struct v4l2_mbus_frame_desc_entry - media bus frame description structure * * @flags: bitmask flags, as defined by &enum v4l2_mbus_frame_desc_flags. + * @stream: stream in routing configuration * @pixelcode: media bus pixel code, valid if @flags * %FRAME_DESC_FL_BLOB is not set. * @length: number of octets per frame, valid if @flags @@ -356,6 +357,7 @@ enum v4l2_mbus_frame_desc_flags { */ struct v4l2_mbus_frame_desc_entry { enum v4l2_mbus_frame_desc_flags flags; + u32 stream; u32 pixelcode; u32 length; union { From patchwork Thu Aug 23 13:25:38 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573899 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 9285613B6 for ; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 8A5E62BE0E for ; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 7EC752C0FF; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B17BF2BE0E for ; Thu, 23 Aug 2018 13:28:21 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730989AbeHWQ6D (ORCPT ); Thu, 23 Aug 2018 12:58:03 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12485 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730851AbeHWQ6C (ORCPT ); Thu, 23 Aug 2018 12:58:02 -0400 X-Halon-ID: 65e55e80-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 65e55e80-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:19 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 24/30] adv748x: csi2: add translation from pixelcode to CSI-2 datatype Date: Thu, 23 Aug 2018 15:25:38 +0200 Message-Id: <20180823132544.521-25-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Prepare to implement frame descriptors to support multiplexed streams by adding a function to map pixelcode to CSI-2 datatype. This is needed to properly be able to fill out the struct v4l2_mbus_frame_desc. Signed-off-by: Niklas Söderlund --- drivers/media/i2c/adv748x/adv748x-csi2.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/drivers/media/i2c/adv748x/adv748x-csi2.c b/drivers/media/i2c/adv748x/adv748x-csi2.c index 469be87a3761feb5..b759a7e22fbc98df 100644 --- a/drivers/media/i2c/adv748x/adv748x-csi2.c +++ b/drivers/media/i2c/adv748x/adv748x-csi2.c @@ -18,6 +18,28 @@ #include "adv748x.h" +struct adv748x_csi2_format { + unsigned int code; + unsigned int datatype; +}; + +static const struct adv748x_csi2_format adv748x_csi2_formats[] = { + { .code = MEDIA_BUS_FMT_RGB888_1X24, .datatype = 0x24, }, + { .code = MEDIA_BUS_FMT_UYVY8_1X16, .datatype = 0x1e, }, + { .code = MEDIA_BUS_FMT_UYVY8_2X8, .datatype = 0x1e, }, + { .code = MEDIA_BUS_FMT_YUYV10_2X10, .datatype = 0x1e, }, +}; + +static unsigned int adv748x_csi2_code_to_datatype(unsigned int code) +{ + unsigned int i; + + for (i = 0; i < ARRAY_SIZE(adv748x_csi2_formats); i++) + if (adv748x_csi2_formats[i].code == code) + return adv748x_csi2_formats[i].datatype; + return 0; +} + static bool is_txa(struct adv748x_csi2 *tx) { return tx == &tx->state->txa; From patchwork Thu Aug 23 13:25:39 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573901 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id C1DF21579 for ; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id BE2952BE0E for ; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id B24872C0FE; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 621152BE23 for ; Thu, 23 Aug 2018 13:28:23 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730908AbeHWQ6E (ORCPT ); Thu, 23 Aug 2018 12:58:04 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12504 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730983AbeHWQ6D (ORCPT ); Thu, 23 Aug 2018 12:58:03 -0400 X-Halon-ID: 6660eee1-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6660eee1-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:19 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 25/30] adv748x: csi2: only allow formats on sink pads Date: Thu, 23 Aug 2018 15:25:39 +0200 Message-Id: <20180823132544.521-26-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Once the CSI-2 subdevice of the ADV748X becomes aware of multiplexed streams the format of the source pad is of no value as it carries multiple streams. Prepare for this by explicitly denying setting a format on anything but the sink pad. Signed-off-by: Niklas Söderlund --- drivers/media/i2c/adv748x/adv748x-csi2.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/media/i2c/adv748x/adv748x-csi2.c b/drivers/media/i2c/adv748x/adv748x-csi2.c index b759a7e22fbc98df..9f736da2ad60160f 100644 --- a/drivers/media/i2c/adv748x/adv748x-csi2.c +++ b/drivers/media/i2c/adv748x/adv748x-csi2.c @@ -172,6 +172,9 @@ static int adv748x_csi2_get_format(struct v4l2_subdev *sd, struct adv748x_state *state = tx->state; struct v4l2_mbus_framefmt *mbusformat; + if (sdformat->pad != ADV748X_CSI2_SINK) + return -EINVAL; + mbusformat = adv748x_csi2_get_pad_format(sd, cfg, sdformat->pad, sdformat->which); if (!mbusformat) @@ -195,6 +198,9 @@ static int adv748x_csi2_set_format(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mbusformat; int ret = 0; + if (sdformat->pad != ADV748X_CSI2_SINK) + return -EINVAL; + mbusformat = adv748x_csi2_get_pad_format(sd, cfg, sdformat->pad, sdformat->which); if (!mbusformat) From patchwork Thu Aug 23 13:25:40 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573907 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id A67DF1926 for ; Thu, 23 Aug 2018 13:28:24 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A44C22B736 for ; Thu, 23 Aug 2018 13:28:24 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 988C82BE0E; Thu, 23 Aug 2018 13:28:24 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 3AF062BE23 for ; Thu, 23 Aug 2018 13:28:24 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1729541AbeHWQ6F (ORCPT ); Thu, 23 Aug 2018 12:58:05 -0400 Received: from bin-mail-out-06.binero.net ([195.74.38.229]:12529 "EHLO bin-mail-out-06.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730851AbeHWQ6E (ORCPT ); Thu, 23 Aug 2018 12:58:04 -0400 X-Halon-ID: 66e433e8-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 66e433e8-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:20 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 26/30] adv748x: csi2: describe the multiplexed stream Date: Thu, 23 Aug 2018 15:25:40 +0200 Message-Id: <20180823132544.521-27-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP The adv748x CSI-2 transmitter can only transmit one stream over the CSI-2 link, however it can choose which virtual channel is used. This choice effects the CSI-2 receiver and needs to be captured in the frame descriptor information, solve this by implementing .get_frame_desc(). Signed-off-by: Niklas Söderlund --- drivers/media/i2c/adv748x/adv748x-csi2.c | 31 +++++++++++++++++++++++- drivers/media/i2c/adv748x/adv748x.h | 1 + 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/drivers/media/i2c/adv748x/adv748x-csi2.c b/drivers/media/i2c/adv748x/adv748x-csi2.c index 9f736da2ad60160f..5087b87a2c2e8f7d 100644 --- a/drivers/media/i2c/adv748x/adv748x-csi2.c +++ b/drivers/media/i2c/adv748x/adv748x-csi2.c @@ -231,9 +231,37 @@ static int adv748x_csi2_set_format(struct v4l2_subdev *sd, return ret; } +static int adv748x_csi2_get_frame_desc(struct v4l2_subdev *sd, unsigned int pad, + struct v4l2_mbus_frame_desc *fd) +{ + struct adv748x_csi2 *tx = adv748x_sd_to_csi2(sd); + struct v4l2_mbus_framefmt *mbusformat; + + memset(fd, 0, sizeof(*fd)); + + if (pad != ADV748X_CSI2_SOURCE) + return -EINVAL; + + mbusformat = adv748x_csi2_get_pad_format(sd, NULL, ADV748X_CSI2_SINK, + V4L2_SUBDEV_FORMAT_ACTIVE); + if (!mbusformat) + return -EINVAL; + + fd->entry->stream = tx->vc; + fd->entry->bus.csi2.channel = tx->vc; + fd->entry->bus.csi2.data_type = + adv748x_csi2_code_to_datatype(mbusformat->code); + + fd->type = V4L2_MBUS_FRAME_DESC_TYPE_CSI2; + fd->num_entries = 1; + + return 0; +} + static const struct v4l2_subdev_pad_ops adv748x_csi2_pad_ops = { .get_fmt = adv748x_csi2_get_format, .set_fmt = adv748x_csi2_set_format, + .get_frame_desc = adv748x_csi2_get_frame_desc, }; /* ----------------------------------------------------------------------------- @@ -309,7 +337,8 @@ int adv748x_csi2_init(struct adv748x_state *state, struct adv748x_csi2 *tx) } /* Initialise the virtual channel */ - adv748x_csi2_set_virtual_channel(tx, 0); + tx->vc = 0; + adv748x_csi2_set_virtual_channel(tx, tx->vc); adv748x_subdev_init(&tx->sd, state, &adv748x_csi2_ops, MEDIA_ENT_F_VID_IF_BRIDGE, diff --git a/drivers/media/i2c/adv748x/adv748x.h b/drivers/media/i2c/adv748x/adv748x.h index 65f83741277e1365..90901b8a4e027ae5 100644 --- a/drivers/media/i2c/adv748x/adv748x.h +++ b/drivers/media/i2c/adv748x/adv748x.h @@ -80,6 +80,7 @@ enum adv748x_csi2_pads { struct adv748x_csi2 { struct adv748x_state *state; + unsigned int vc; struct v4l2_mbus_framefmt format; unsigned int page; From patchwork Thu Aug 23 13:25:41 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573911 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id B8AEA1579 for ; Thu, 23 Aug 2018 13:28:25 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B4ADD2B736 for ; Thu, 23 Aug 2018 13:28:25 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id A8F5A2BE0E; Thu, 23 Aug 2018 13:28:25 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 503102B736 for ; Thu, 23 Aug 2018 13:28:25 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730043AbeHWQ6G (ORCPT ); Thu, 23 Aug 2018 12:58:06 -0400 Received: from vsp-unauthed02.binero.net ([195.74.38.227]:12550 "EHLO vsp-unauthed02.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1730851AbeHWQ6F (ORCPT ); Thu, 23 Aug 2018 12:58:05 -0400 X-Halon-ID: 6772175b-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6772175b-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:21 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 27/30] adv748x: csi2: add internal routing configuration Date: Thu, 23 Aug 2018 15:25:41 +0200 Message-Id: <20180823132544.521-28-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add support to get and set the internal routing between the adv748x CSI-2 transmitters sink pad and its multiplexed source pad. This routing includes which stream of the multiplexed pad to use, allowing the user to select which CSI-2 virtual channel to use when transmitting the stream. Signed-off-by: Niklas Söderlund --- drivers/media/i2c/adv748x/adv748x-csi2.c | 65 ++++++++++++++++++++++++ 1 file changed, 65 insertions(+) diff --git a/drivers/media/i2c/adv748x/adv748x-csi2.c b/drivers/media/i2c/adv748x/adv748x-csi2.c index 5087b87a2c2e8f7d..7bd4566807d0a4ee 100644 --- a/drivers/media/i2c/adv748x/adv748x-csi2.c +++ b/drivers/media/i2c/adv748x/adv748x-csi2.c @@ -18,6 +18,8 @@ #include "adv748x.h" +#define ADV748X_CSI2_ROUTES_MAX 4 + struct adv748x_csi2_format { unsigned int code; unsigned int datatype; @@ -258,10 +260,73 @@ static int adv748x_csi2_get_frame_desc(struct v4l2_subdev *sd, unsigned int pad, return 0; } +static int adv748x_csi2_get_routing(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *routing) +{ + struct adv748x_csi2 *tx = adv748x_sd_to_csi2(sd); + struct v4l2_subdev_route *r = routing->routes; + unsigned int vc; + + if (routing->num_routes < ADV748X_CSI2_ROUTES_MAX) { + routing->num_routes = ADV748X_CSI2_ROUTES_MAX; + return -ENOSPC; + } + + routing->num_routes = ADV748X_CSI2_ROUTES_MAX; + + for (vc = 0; vc < ADV748X_CSI2_ROUTES_MAX; vc++) { + r->sink_pad = ADV748X_CSI2_SINK; + r->sink_stream = 0; + r->source_pad = ADV748X_CSI2_SOURCE; + r->source_stream = vc; + r->flags = vc == tx->vc ? V4L2_SUBDEV_ROUTE_FL_ACTIVE : 0; + r++; + } + + return 0; +} + +static int adv748x_csi2_set_routing(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *routing) +{ + struct adv748x_csi2 *tx = adv748x_sd_to_csi2(sd); + struct v4l2_subdev_route *r = routing->routes; + unsigned int i; + int vc = -1; + + if (routing->num_routes > ADV748X_CSI2_ROUTES_MAX) + return -ENOSPC; + + for (i = 0; i < routing->num_routes; i++) { + if (r->sink_pad != ADV748X_CSI2_SINK || + r->sink_stream != 0 || + r->source_pad != ADV748X_CSI2_SOURCE || + r->source_stream >= ADV748X_CSI2_ROUTES_MAX) + return -EINVAL; + + if (r->flags & V4L2_SUBDEV_ROUTE_FL_ACTIVE) { + if (vc != -1) + return -EMLINK; + + vc = r->source_stream; + } + r++; + } + + if (vc != -1) + tx->vc = vc; + + adv748x_csi2_set_virtual_channel(tx, tx->vc); + + return 0; +} + static const struct v4l2_subdev_pad_ops adv748x_csi2_pad_ops = { .get_fmt = adv748x_csi2_get_format, .set_fmt = adv748x_csi2_set_format, .get_frame_desc = adv748x_csi2_get_frame_desc, + .get_routing = adv748x_csi2_get_routing, + .set_routing = adv748x_csi2_set_routing, }; /* ----------------------------------------------------------------------------- From patchwork Thu Aug 23 13:25:42 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573915 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id BA6251579 for ; Thu, 23 Aug 2018 13:28:26 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B81C32B736 for ; Thu, 23 Aug 2018 13:28:26 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id ACB4E2BE23; Thu, 23 Aug 2018 13:28:26 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 5B59F2B737 for ; Thu, 23 Aug 2018 13:28:26 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731103AbeHWQ6G (ORCPT ); Thu, 23 Aug 2018 12:58:06 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12572 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1731034AbeHWQ6G (ORCPT ); Thu, 23 Aug 2018 12:58:06 -0400 X-Halon-ID: 67f40d23-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 67f40d23-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:22 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 28/30] adv748x: afe: add routing support Date: Thu, 23 Aug 2018 15:25:42 +0200 Message-Id: <20180823132544.521-29-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP The adv748x afe has eight analog sink pads, currently one of them is chosen to be the active route based on device tree configuration. With the new routing API it's possible to expose and change which of the eight sink pads are routed to the source pad. Signed-off-by: Niklas Söderlund --- drivers/media/i2c/adv748x/adv748x-afe.c | 65 +++++++++++++++++++++++++ 1 file changed, 65 insertions(+) diff --git a/drivers/media/i2c/adv748x/adv748x-afe.c b/drivers/media/i2c/adv748x/adv748x-afe.c index edd25e895e5dec3c..dac0e9e385e7791a 100644 --- a/drivers/media/i2c/adv748x/adv748x-afe.c +++ b/drivers/media/i2c/adv748x/adv748x-afe.c @@ -43,6 +43,9 @@ #define ADV748X_AFE_STD_PAL_SECAM 0xe #define ADV748X_AFE_STD_PAL_SECAM_PED 0xf +#define ADV748X_AFE_ROUTES_MAX ((ADV748X_AFE_SINK_AIN7 - \ + ADV748X_AFE_SINK_AIN0) + 1) + static int adv748x_afe_read_ro_map(struct adv748x_state *state, u8 reg) { int ret; @@ -387,10 +390,72 @@ static int adv748x_afe_set_format(struct v4l2_subdev *sd, return 0; } +static int adv748x_afe_get_routing(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *routing) +{ + struct adv748x_afe *afe = adv748x_sd_to_afe(sd); + struct v4l2_subdev_route *r = routing->routes; + unsigned int i; + + /* There is one possible route from each sink */ + if (routing->num_routes < ADV748X_AFE_ROUTES_MAX) { + routing->num_routes = ADV748X_AFE_ROUTES_MAX; + return -ENOSPC; + } + + routing->num_routes = ADV748X_AFE_ROUTES_MAX; + + for (i = ADV748X_AFE_SINK_AIN0; i <= ADV748X_AFE_SINK_AIN7; i++) { + r->sink_pad = i; + r->sink_stream = 0; + r->source_pad = ADV748X_AFE_SOURCE; + r->source_stream = 0; + r->flags = afe->input == i ? V4L2_SUBDEV_ROUTE_FL_ACTIVE : 0; + r++; + } + + return 0; +} + +static int adv748x_afe_set_routing(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *routing) +{ + struct adv748x_afe *afe = adv748x_sd_to_afe(sd); + struct v4l2_subdev_route *r = routing->routes; + int input = -1; + unsigned int i; + + if (routing->num_routes > ADV748X_AFE_ROUTES_MAX) + return -ENOSPC; + + for (i = 0; i < routing->num_routes; i++) { + if (r->sink_pad > ADV748X_AFE_SINK_AIN7 || + r->sink_stream != 0 || + r->source_pad != ADV748X_AFE_SOURCE || + r->source_stream != 0) + return -EINVAL; + + if (r->flags & V4L2_SUBDEV_ROUTE_FL_ACTIVE) { + if (input != -1) + return -EMLINK; + + input = r->sink_pad; + } + r++; + } + + if (input != -1) + afe->input = input; + + return 0; +} + static const struct v4l2_subdev_pad_ops adv748x_afe_pad_ops = { .enum_mbus_code = adv748x_afe_enum_mbus_code, .set_fmt = adv748x_afe_set_format, .get_fmt = adv748x_afe_get_format, + .get_routing = adv748x_afe_get_routing, + .set_routing = adv748x_afe_set_routing, }; /* ----------------------------------------------------------------------------- From patchwork Thu Aug 23 13:25:43 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573917 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 612BE139B for ; Thu, 23 Aug 2018 13:28:27 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 5DF1B2B736 for ; Thu, 23 Aug 2018 13:28:27 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 524622BE23; Thu, 23 Aug 2018 13:28:27 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 829C22BE0E for ; Thu, 23 Aug 2018 13:28:26 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731118AbeHWQ6I (ORCPT ); Thu, 23 Aug 2018 12:58:08 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12586 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1729976AbeHWQ6H (ORCPT ); Thu, 23 Aug 2018 12:58:07 -0400 X-Halon-ID: 6882755c-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6882755c-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:23 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 29/30] rcar-csi2: use frame description information to configure CSI-2 bus Date: Thu, 23 Aug 2018 15:25:43 +0200 Message-Id: <20180823132544.521-30-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP The driver can now access frame descriptor information, use it when configuring the CSI-2 bus. Only enable the virtual channels which are described in the frame descriptor and calculate the link based on all enabled streams. With multiplexed stream supported it's now meaningful to have different formats on the different source pads. Make source formats independent off each other and disallowing a format on the multiplexed sink pad. Signed-off-by: Niklas Söderlund --- drivers/media/platform/rcar-vin/rcar-csi2.c | 135 ++++++++++++++------ 1 file changed, 98 insertions(+), 37 deletions(-) diff --git a/drivers/media/platform/rcar-vin/rcar-csi2.c b/drivers/media/platform/rcar-vin/rcar-csi2.c index dc5ae8025832ab6e..467722007b328e4e 100644 --- a/drivers/media/platform/rcar-vin/rcar-csi2.c +++ b/drivers/media/platform/rcar-vin/rcar-csi2.c @@ -304,25 +304,22 @@ static const struct rcsi2_mbps_reg hsfreqrange_m3w_h3es1[] = { #define CSI0CLKFREQRANGE(n) ((n & 0x3f) << 16) struct rcar_csi2_format { - u32 code; unsigned int datatype; unsigned int bpp; }; static const struct rcar_csi2_format rcar_csi2_formats[] = { - { .code = MEDIA_BUS_FMT_RGB888_1X24, .datatype = 0x24, .bpp = 24 }, - { .code = MEDIA_BUS_FMT_UYVY8_1X16, .datatype = 0x1e, .bpp = 16 }, - { .code = MEDIA_BUS_FMT_YUYV8_1X16, .datatype = 0x1e, .bpp = 16 }, - { .code = MEDIA_BUS_FMT_UYVY8_2X8, .datatype = 0x1e, .bpp = 16 }, - { .code = MEDIA_BUS_FMT_YUYV10_2X10, .datatype = 0x1e, .bpp = 20 }, + { .datatype = 0x1e, .bpp = 16 }, + { .datatype = 0x24, .bpp = 24 }, }; -static const struct rcar_csi2_format *rcsi2_code_to_fmt(unsigned int code) +static const struct rcar_csi2_format +*rcsi2_datatype_to_fmt(unsigned int datatype) { unsigned int i; for (i = 0; i < ARRAY_SIZE(rcar_csi2_formats); i++) - if (rcar_csi2_formats[i].code == code) + if (rcar_csi2_formats[i].datatype == datatype) return &rcar_csi2_formats[i]; return NULL; @@ -337,6 +334,14 @@ enum rcar_csi2_pads { NR_OF_RCAR_CSI2_PAD, }; +static int rcsi2_pad_to_vc(unsigned int pad) +{ + if (pad < RCAR_CSI2_SOURCE_VC0 || pad > RCAR_CSI2_SOURCE_VC3) + return -EINVAL; + + return pad - RCAR_CSI2_SOURCE_VC0; +} + struct rcar_csi2_info { int (*init_phtw)(struct rcar_csi2 *priv, unsigned int mbps); int (*confirm_start)(struct rcar_csi2 *priv); @@ -357,7 +362,7 @@ struct rcar_csi2 { struct v4l2_async_subdev asd; struct v4l2_subdev *remote; - struct v4l2_mbus_framefmt mf; + struct v4l2_mbus_framefmt mf[4]; struct mutex lock; int stream_count; @@ -393,6 +398,32 @@ static void rcsi2_reset(struct rcar_csi2 *priv) rcsi2_write(priv, SRST_REG, 0); } +static int rcsi2_get_remote_frame_desc(struct rcar_csi2 *priv, + struct v4l2_mbus_frame_desc *fd) +{ + struct media_pad *pad; + int ret; + + if (!priv->remote) + return -ENODEV; + + pad = media_entity_remote_pad(&priv->pads[RCAR_CSI2_SINK]); + if (!pad) + return -ENODEV; + + ret = v4l2_subdev_call(priv->remote, pad, get_frame_desc, + pad->index, fd); + if (ret) + return -ENODEV; + + if (fd->type != V4L2_MBUS_FRAME_DESC_TYPE_CSI2) { + dev_err(priv->dev, "Frame desc do not describe CSI-2 link"); + return -EINVAL; + } + + return 0; +} + static int rcsi2_wait_phy_start(struct rcar_csi2 *priv) { unsigned int timeout; @@ -431,10 +462,12 @@ static int rcsi2_set_phypll(struct rcar_csi2 *priv, unsigned int mbps) return 0; } -static int rcsi2_calc_mbps(struct rcar_csi2 *priv, unsigned int bpp) +static int rcsi2_calc_mbps(struct rcar_csi2 *priv, + struct v4l2_mbus_frame_desc *fd) { struct v4l2_subdev *source; struct v4l2_ctrl *ctrl; + unsigned int i, bpp = 0; u64 mbps; if (!priv->remote) @@ -450,6 +483,21 @@ static int rcsi2_calc_mbps(struct rcar_csi2 *priv, unsigned int bpp) return -EINVAL; } + /* Calculate total bpp */ + for (i = 0; i < fd->num_entries; i++) { + const struct rcar_csi2_format *format; + + format = rcsi2_datatype_to_fmt( + fd->entry[i].bus.csi2.data_type); + if (!format) { + dev_err(priv->dev, "Unknown data type: %d\n", + fd->entry[i].bus.csi2.data_type); + return -EINVAL; + } + + bpp += format->bpp; + } + /* * Calculate the phypll in mbps. * link_freq = (pixel_rate * bits_per_sample) / (2 * nr_of_lanes) @@ -463,42 +511,40 @@ static int rcsi2_calc_mbps(struct rcar_csi2 *priv, unsigned int bpp) static int rcsi2_start(struct rcar_csi2 *priv) { - const struct rcar_csi2_format *format; + struct v4l2_mbus_frame_desc fd; u32 phycnt, vcdt = 0, vcdt2 = 0; unsigned int i; int mbps, ret; - dev_dbg(priv->dev, "Input size (%ux%u%c)\n", - priv->mf.width, priv->mf.height, - priv->mf.field == V4L2_FIELD_NONE ? 'p' : 'i'); - - /* Code is validated in set_fmt. */ - format = rcsi2_code_to_fmt(priv->mf.code); + /* Get information about multiplexed link. */ + ret = rcsi2_get_remote_frame_desc(priv, &fd); + if (ret) + return ret; - /* - * Enable all Virtual Channels. - * - * NOTE: It's not possible to get individual datatype for each - * source virtual channel. Once this is possible in V4L2 - * it should be used here. - */ - for (i = 0; i < 4; i++) { + for (i = 0; i < fd.num_entries; i++) { + struct v4l2_mbus_frame_desc_entry *entry = &fd.entry[i]; u32 vcdt_part; - vcdt_part = VCDT_SEL_VC(i) | VCDT_VCDTN_EN | VCDT_SEL_DTN_ON | - VCDT_SEL_DT(format->datatype); + vcdt_part = VCDT_SEL_VC(entry->bus.csi2.channel) | + VCDT_VCDTN_EN | VCDT_SEL_DTN_ON | + VCDT_SEL_DT(entry->bus.csi2.data_type); /* Store in correct reg and offset. */ - if (i < 2) - vcdt |= vcdt_part << ((i % 2) * 16); + if (entry->bus.csi2.channel < 2) + vcdt |= vcdt_part << + ((entry->bus.csi2.channel % 2) * 16); else - vcdt2 |= vcdt_part << ((i % 2) * 16); + vcdt2 |= vcdt_part << + ((entry->bus.csi2.channel % 2) * 16); + + dev_dbg(priv->dev, "VC%d datatype: 0x%x\n", + entry->bus.csi2.channel, entry->bus.csi2.data_type); } phycnt = PHYCNT_ENABLECLK; phycnt |= (1 << priv->lanes) - 1; - mbps = rcsi2_calc_mbps(priv, format->bpp); + mbps = rcsi2_calc_mbps(priv, &fd); if (mbps < 0) return mbps; @@ -619,14 +665,16 @@ static int rcsi2_set_pad_format(struct v4l2_subdev *sd, { struct rcar_csi2 *priv = sd_to_csi2(sd); struct v4l2_mbus_framefmt *framefmt; + int vc; - if (!rcsi2_code_to_fmt(format->format.code)) - format->format.code = rcar_csi2_formats[0].code; + vc = rcsi2_pad_to_vc(format->pad); + if (vc < 0) + return vc; if (format->which == V4L2_SUBDEV_FORMAT_ACTIVE) { - priv->mf = format->format; + priv->mf[vc] = format->format; } else { - framefmt = v4l2_subdev_get_try_format(sd, cfg, 0); + framefmt = v4l2_subdev_get_try_format(sd, cfg, format->pad); *framefmt = format->format; } @@ -638,11 +686,17 @@ static int rcsi2_get_pad_format(struct v4l2_subdev *sd, struct v4l2_subdev_format *format) { struct rcar_csi2 *priv = sd_to_csi2(sd); + int vc; + + vc = rcsi2_pad_to_vc(format->pad); + if (vc < 0) + return vc; if (format->which == V4L2_SUBDEV_FORMAT_ACTIVE) - format->format = priv->mf; + format->format = priv->mf[vc]; else - format->format = *v4l2_subdev_get_try_format(sd, cfg, 0); + format->format = *v4l2_subdev_get_try_format(sd, cfg, + format->pad); return 0; } @@ -672,6 +726,13 @@ static int rcsi2_notify_bound(struct v4l2_async_notifier *notifier, struct rcar_csi2 *priv = notifier_to_csi2(notifier); int pad; + if (!v4l2_subdev_has_op(subdev, pad, get_frame_desc)) { + dev_err(priv->dev, + "Failed as '%s' do not support frame descriptors\n", + subdev->name); + return -EINVAL; + } + pad = media_entity_get_fwnode_pad(&subdev->entity, asd->match.fwnode, MEDIA_PAD_FL_SOURCE); if (pad < 0) { From patchwork Thu Aug 23 13:25:44 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Niklas_S=C3=B6derlund?= X-Patchwork-Id: 10573923 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id A0D1A1926 for ; Thu, 23 Aug 2018 13:28:28 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 9D3EB2B737 for ; Thu, 23 Aug 2018 13:28:28 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 8D7E92C0FF; Thu, 23 Aug 2018 13:28:28 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.9 required=2.0 tests=BAYES_00,MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI autolearn=unavailable version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4327D2BE0E for ; Thu, 23 Aug 2018 13:28:28 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730851AbeHWQ6J (ORCPT ); Thu, 23 Aug 2018 12:58:09 -0400 Received: from bin-mail-out-05.binero.net ([195.74.38.228]:12604 "EHLO bin-mail-out-05.binero.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1731012AbeHWQ6I (ORCPT ); Thu, 23 Aug 2018 12:58:08 -0400 X-Halon-ID: 6926d282-a6d8-11e8-8edf-005056917f90 Authorized-sender: niklas@soderlund.pp.se Received: from bismarck.berto.se (unknown [89.233.230.99]) by bin-vsp-out-02.atm.binero.net (Halon) with ESMTPA id 6926d282-a6d8-11e8-8edf-005056917f90; Thu, 23 Aug 2018 15:28:24 +0200 (CEST) From: =?utf-8?q?Niklas_S=C3=B6derlund?= To: Laurent Pinchart , Sakari Ailus , linux-media@vger.kernel.org Cc: linux-renesas-soc@vger.kernel.org, =?utf-8?q?Niklas_S=C3=B6derlund?= Subject: [PATCH 30/30] rcar-csi2: expose the subdevice internal routing Date: Thu, 23 Aug 2018 15:25:44 +0200 Message-Id: <20180823132544.521-31-niklas.soderlund+renesas@ragnatech.se> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> References: <20180823132544.521-1-niklas.soderlund+renesas@ragnatech.se> MIME-Version: 1.0 Sender: linux-renesas-soc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-renesas-soc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Expose the subdevice internal routing from the single multiplexed sink pad to its source pads by implementing .get_routing(). This information is used to do link validation at stream start and allows user-space to view the route configuration. Signed-off-by: Niklas Söderlund --- drivers/media/platform/rcar-vin/rcar-csi2.c | 53 +++++++++++++++++++++ 1 file changed, 53 insertions(+) diff --git a/drivers/media/platform/rcar-vin/rcar-csi2.c b/drivers/media/platform/rcar-vin/rcar-csi2.c index 467722007b328e4e..1cd17f4091946cad 100644 --- a/drivers/media/platform/rcar-vin/rcar-csi2.c +++ b/drivers/media/platform/rcar-vin/rcar-csi2.c @@ -342,6 +342,14 @@ static int rcsi2_pad_to_vc(unsigned int pad) return pad - RCAR_CSI2_SOURCE_VC0; } +static int rcsi2_vc_to_pad(unsigned int vc) +{ + if (vc > 3) + return -EINVAL; + + return vc + RCAR_CSI2_SOURCE_VC0; +} + struct rcar_csi2_info { int (*init_phtw)(struct rcar_csi2 *priv, unsigned int mbps); int (*confirm_start)(struct rcar_csi2 *priv); @@ -705,9 +713,54 @@ static const struct v4l2_subdev_video_ops rcar_csi2_video_ops = { .s_stream = rcsi2_s_stream, }; +static int rcsi2_get_routing(struct v4l2_subdev *sd, + struct v4l2_subdev_routing *routing) +{ + struct rcar_csi2 *priv = sd_to_csi2(sd); + struct v4l2_mbus_frame_desc fd; + struct v4l2_subdev_route *r = routing->routes; + unsigned int i; + int ret; + + /* Get information about multiplexed link */ + ret = rcsi2_get_remote_frame_desc(priv, &fd); + if (ret) + return ret; + + if (routing->num_routes < fd.num_entries) { + routing->num_routes = fd.num_entries; + return -ENOSPC; + } + + routing->num_routes = fd.num_entries; + + for (i = 0; i < fd.num_entries; i++) { + struct v4l2_mbus_frame_desc_entry *entry = &fd.entry[i]; + int source_pad; + + source_pad = rcsi2_vc_to_pad(entry->bus.csi2.channel); + if (source_pad < 0) { + dev_err(priv->dev, "Virtual Channel out of range: %u\n", + entry->bus.csi2.channel); + return -ENOSPC; + } + + r->sink_pad = RCAR_CSI2_SINK; + r->sink_stream = entry->stream; + r->source_pad = source_pad; + r->source_stream = 0; + r->flags = V4L2_SUBDEV_ROUTE_FL_ACTIVE | + V4L2_SUBDEV_ROUTE_FL_IMMUTABLE; + r++; + } + + return 0; +} + static const struct v4l2_subdev_pad_ops rcar_csi2_pad_ops = { .set_fmt = rcsi2_set_pad_format, .get_fmt = rcsi2_get_pad_format, + .get_routing = rcsi2_get_routing, }; static const struct v4l2_subdev_ops rcar_csi2_subdev_ops = {