linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Shengjiu Wang <shengjiu.wang@gmail.com>
To: Liu Ying <victor.liu@nxp.com>
Cc: Shengjiu Wang <shengjiu.wang@nxp.com>,
	andrzej.hajda@intel.com,  neil.armstrong@linaro.org,
	rfoss@kernel.org,  Laurent.pinchart@ideasonboard.com,
	jonas@kwiboo.se, jernej.skrabec@gmail.com,
	 maarten.lankhorst@linux.intel.com, mripard@kernel.org,
	tzimmermann@suse.de,  airlied@gmail.com, simona@ffwll.ch,
	lumag@kernel.org, dianders@chromium.org,
	 cristian.ciocaltea@collabora.com, luca.ceresoli@bootlin.com,
	 dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org,
	 shawnguo@kernel.org, s.hauer@pengutronix.de,
	kernel@pengutronix.de,  festevam@gmail.com, imx@lists.linux.dev,
	linux-arm-kernel@lists.infradead.org,  robh@kernel.org,
	krzk+dt@kernel.org, conor+dt@kernel.org,  p.zabel@pengutronix.de,
	devicetree@vger.kernel.org, l.stach@pengutronix.de,
	 perex@perex.cz, tiwai@suse.com, linux-sound@vger.kernel.org
Subject: Re: [PATCH v3 5/6] drm/bridge: imx: add driver for HDMI TX Parallel Audio Interface
Date: Thu, 7 Aug 2025 18:58:15 +0800	[thread overview]
Message-ID: <CAA+D8AN3VzFx1g=8wyxJROw96xS2-qoVs3X4vUfFnJtUCqFj_w@mail.gmail.com> (raw)
In-Reply-To: <ba02693b-8ad2-4297-ab89-5b39d5c4315f@nxp.com>

On Wed, Aug 6, 2025 at 2:52 PM Liu Ying <victor.liu@nxp.com> wrote:
>
> On 08/06/2025, Shengjiu Wang wrote:
> > On Tue, Aug 5, 2025 at 4:55 PM Liu Ying <victor.liu@nxp.com> wrote:
> >>
> >> On 08/04/2025, Shengjiu Wang wrote:
>
> [...]
>
> >>> +static int imx8mp_hdmi_pai_bind(struct device *dev, struct device *master, void *data)
> >>> +{
> >>> +     struct dw_hdmi_plat_data *plat_data = (struct dw_hdmi_plat_data *)data;
> >>> +     struct imx8mp_hdmi_pai *hdmi_pai;
> >>> +
> >>> +     hdmi_pai = dev_get_drvdata(dev);
> >>> +
> >>> +     plat_data->enable_audio = imx8mp_hdmi_pai_enable;
> >>> +     plat_data->disable_audio = imx8mp_hdmi_pai_disable;
> >>> +     plat_data->priv_audio = hdmi_pai;
> >>> +
> >>> +     return 0;
> >>> +}
> >>> +
> >>> +static void imx8mp_hdmi_pai_unbind(struct device *dev, struct device *master, void *data)
> >>> +{
> >>> +     struct dw_hdmi_plat_data *plat_data = (struct dw_hdmi_plat_data *)data;
> >>> +
> >>> +     plat_data->enable_audio = NULL;
> >>> +     plat_data->disable_audio = NULL;
> >>> +     plat_data->priv_audio = NULL;
> >>
> >> Do you really need to set these ptrs to NULL?
> >
> > yes.  below code in dw-hdmi.c use the pdata->enable_audio as condition.
>
> Note that this is all about tearing down components.
> If this is done properly as the below snippet of pseudo-code, then
> hdmi->{enable,disable}_audio() and pdata->{enable,disable}_audio() won't be
> called after audio device is removed by dw_hdmi_remove().  So, it's unnecessary
> to set these pointers to NULL here.
>
> imx8mp_dw_hdmi_unbind()
> {
>    dw_hdmi_remove(); // platform_device_unregister(hdmi->audio);
>    component_unbind_all(); //imx8mp_hdmi_pai_unbind()
> }
>
> BTW, I suggest the below snippet[1] to bind components.
>
> imx8mp_dw_hdmi_bind()
> {
>    component_bind_all(); // imx8mp_hdmi_pai_bind()
>                          //   set pdata->{enable,disable}_audio
>    dw_hdmi_probe(); // hdmi->audio = platform_device_register_full(&pdevinfo);
> }

Looks like we should use dw_hdmi_bind() here to make unbind -> bind work.
But can't get the encoder pointer.  the encoder pointer is from lcdif_drv.c,
the probe sequence of lcdif, pvi, dw_hdmi should be dw_hdmi first, then pvi,
then lcdif, because current implementation in lcdif and pvi driver.

Should the lcdif and pvi driver be modified to use component helper?
This seems out of the scope of this patch set.

Best regards
Shengjiu Wang
>
> >
> >         if (pdata->enable_audio)
> >                 pdata->enable_audio(hdmi,
> >                                     hdmi->channels,
> >                                     hdmi->sample_width,
> >                                     hdmi->sample_rate,
> >                                     hdmi->sample_non_pcm,
> >                                     hdmi->sample_iec958);
> >
> >
> >>
>
> [...]
>
> >>> +     return component_add(dev, &imx8mp_hdmi_pai_ops);
> >>
> >> Imagine that users could enable this driver without enabling imx8mp-hdmi-tx
> >> driver, you may add the component in this probe() callback only and move all
> >> the other stuff to bind() callback to avoid unnecessary things being done here.
> >
> > component helper functions don't have such dependency that the aggregate
> > driver or component driver must be probed or not.  if imx8mp-hdmi-tx is not
> > enabled, there is no problem, just the bind() callback is not called.
>
> I meant I'd write imx8mp_hdmi_pai_probe() as below snippet and do all the
> other stuff in imx8mp_hdmi_pai_bind().  This ensures minimum things are done
> in imx8mp_hdmi_pai_probe() if imx8mp-hdmi-tx doesn't probe.
>
> static int imx8mp_hdmi_pai_probe(struct platform_device *pdev)
> {
>         return component_add(&pdev->dev, &imx8mp_hdmi_pai_ops);
> }
>
> >
> >>
> >>> +}
> >>> +
> >>> +static void imx8mp_hdmi_pai_remove(struct platform_device *pdev)
> >>> +{
> >>> +     component_del(&pdev->dev, &imx8mp_hdmi_pai_ops);
> >>> +}
> >>> +
> >>> +static const struct of_device_id imx8mp_hdmi_pai_of_table[] = {
> >>> +     { .compatible = "fsl,imx8mp-hdmi-pai" },
> >>> +     { /* Sentinel */ }
> >>> +};
> >>> +MODULE_DEVICE_TABLE(of, imx8mp_hdmi_pai_of_table);
> >>> +
> >>> +static struct platform_driver imx8mp_hdmi_pai_platform_driver = {
> >>> +     .probe          = imx8mp_hdmi_pai_probe,
> >>> +     .remove         = imx8mp_hdmi_pai_remove,
> >>> +     .driver         = {
> >>> +             .name   = "imx8mp-hdmi-pai",
> >>> +             .of_match_table = imx8mp_hdmi_pai_of_table,
> >>> +     },
> >>> +};
> >>> +module_platform_driver(imx8mp_hdmi_pai_platform_driver);
> >>> +
> >>> +MODULE_DESCRIPTION("i.MX8MP HDMI PAI driver");
> >>> +MODULE_LICENSE("GPL");
> >>> diff --git a/drivers/gpu/drm/bridge/imx/imx8mp-hdmi-tx.c b/drivers/gpu/drm/bridge/imx/imx8mp-hdmi-tx.c
> >>> index 1e7a789ec289..ee08084d2394 100644
> >>> --- a/drivers/gpu/drm/bridge/imx/imx8mp-hdmi-tx.c
> >>> +++ b/drivers/gpu/drm/bridge/imx/imx8mp-hdmi-tx.c
> >>> @@ -5,11 +5,13 @@
> >>>   */
> >>>
> >>>  #include <linux/clk.h>
> >>> +#include <linux/component.h>
> >>>  #include <linux/mod_devicetable.h>
> >>>  #include <linux/module.h>
> >>>  #include <linux/platform_device.h>
> >>>  #include <drm/bridge/dw_hdmi.h>
> >>>  #include <drm/drm_modes.h>
> >>> +#include <drm/drm_of.h>
> >>>
> >>>  struct imx8mp_hdmi {
> >>>       struct dw_hdmi_plat_data plat_data;
> >>> @@ -79,11 +81,46 @@ static const struct dw_hdmi_phy_ops imx8mp_hdmi_phy_ops = {
> >>>       .update_hpd     = dw_hdmi_phy_update_hpd,
> >>>  };
> >>>
> >>> +static int imx8mp_dw_hdmi_bind(struct device *dev)
> >>> +{
> >>> +     struct dw_hdmi_plat_data *plat_data;
> >>> +     struct imx8mp_hdmi *hdmi;
> >>> +     int ret;
> >>> +
> >>> +     hdmi = dev_get_drvdata(dev);
> >>> +     plat_data = &hdmi->plat_data;
> >>> +
> >>> +     ret = component_bind_all(dev, plat_data);
> >>> +     if (ret)
> >>> +             return dev_err_probe(dev, ret, "component_bind_all failed!\n");
> >>
> >> As component_bind_all() would bind imx8mp-hdmi-pai and hence set
> >> {enable,disable}_audio callbacks, you need to call dw_hdmi_probe() after
> >> component_bind_all() instead of too early in probe() callback.
> >
> > There is no such dependency.
> > Maybe you mixed the hdmi->enable_audio() with pdata->enable_audio().
>
> As the above snippet[1] shows, once dw_hdmi_probe() registers audio device,
> the audio device could be functional soon after audio driver probes, hence
> hdmi->enable_audio() would be called and hence pdata->enable_audio() would
> be called. So, you need to set pdata->enable_audio() before dw_hdmi_probe()
> is called, otherwise pdata->enable_audio could be NULL when is called by
> audio driver.
>
> [...]
>
> >>> +     remote = of_graph_get_remote_node(pdev->dev.of_node, 2, 0);
> >>> +     if (remote && of_device_is_available(remote)) {
> >>
> >> Doesn't of_graph_get_remote_node() ensure that remote is avaiable?
> >
> > No.  'remote' is the node,  not the 'device'.
>
> See of_device_is_available() is called by of_graph_get_remote_node():
>
> struct device_node *of_graph_get_remote_node(const struct device_node *node,
>                                              u32 port, u32 endpoint)
> {
>         struct device_node *endpoint_node, *remote;
>
>         endpoint_node = of_graph_get_endpoint_by_regs(node, port, endpoint);
>         if (!endpoint_node) {
>                 pr_debug("no valid endpoint (%d, %d) for node %pOF\n",
>                          port, endpoint, node);
>                 return NULL;
>         }
>
>         remote = of_graph_get_remote_port_parent(endpoint_node);
>         of_node_put(endpoint_node);
>         if (!remote) {
>                 pr_debug("no valid remote node\n");
>                 return NULL;
>         }
>
>         if (!of_device_is_available(remote)) {
>              ^~~~~~~~~~~~~~~~~~~~~~
>                 pr_debug("not available for remote node\n");
>                 of_node_put(remote);
>                 return NULL;
>         }
>
>         return remote;
> }
> EXPORT_SYMBOL(of_graph_get_remote_node);
>
> >
> >>
> >>> +             drm_of_component_match_add(dev, &match, component_compare_of, remote);
> >>> +
> >>> +             of_node_put(remote);
> >>> +
> >>> +             ret = component_master_add_with_match(dev, &imx8mp_dw_hdmi_ops, match);
> >>> +             if (ret)
> >>> +                     dev_warn(dev, "Unable to register aggregate driver\n");
> >>> +             /*
> >>> +              * This audio function is optional for avoid blocking display.
> >>> +              * So just print warning message and no error is returned.
> >>
> >> No, since PAI node is available here, it has to be bound.  Yet you still need
> >> to properly handle the case where PAI node is inavailable.
> >
> > This is for aggregate driver registration,  not for bind()
> >
> > The bind() is called after both drivers have been registered.  again there is no
> > dependency for both aggregate driver and component driver should be
> > registered or probed.
>
> Sorry for not being clear about my previous wording.  I meant since PAI node is
> available here, component_master_add_with_match() must be called to register
> the master and if it fails to register it, imx8mp_dw_hdmi_probe() should return
> proper error code, not 0.
>
> --
> Regards,
> Liu Ying

  reply	other threads:[~2025-08-07 10:58 UTC|newest]

Thread overview: 26+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2025-08-04 10:47 [PATCH v3 0/6] drm/bridge: imx: Add HDMI PAI driver on i.MX8MP Shengjiu Wang
2025-08-04 10:47 ` [PATCH v3 1/6] dt-bindings: display: imx: add HDMI PAI for i.MX8MP Shengjiu Wang
2025-08-05  6:35   ` Krzysztof Kozlowski
2025-08-04 10:47 ` [PATCH v3 2/6] ALSA: Add definitions for the bits in IEC958 subframe Shengjiu Wang
2025-08-04 10:47 ` [PATCH v3 3/6] drm/bridge: dw-hdmi: Add API dw_hdmi_to_plat_data() to get plat_data Shengjiu Wang
2025-08-05  9:00   ` Liu Ying
2025-08-04 10:47 ` [PATCH v3 4/6] drm/bridge: dw-hdmi: Add API dw_hdmi_set_sample_iec958() for iec958 format Shengjiu Wang
2025-08-04 10:47 ` [PATCH v3 5/6] drm/bridge: imx: add driver for HDMI TX Parallel Audio Interface Shengjiu Wang
2025-08-05  7:09   ` Alexander Stein
2025-08-06  3:49     ` Shengjiu Wang
2025-08-07  6:48       ` Alexander Stein
2025-08-07  7:42         ` Shengjiu Wang
2025-08-05  8:56   ` Liu Ying
2025-08-06  5:42     ` Shengjiu Wang
2025-08-06  6:54       ` Liu Ying
2025-08-07 10:58         ` Shengjiu Wang [this message]
2025-08-08  6:34           ` Liu Ying
2025-08-08  6:45             ` Shengjiu Wang
2025-08-08  7:50               ` Liu Ying
2025-08-08  7:52                 ` Shengjiu Wang
2025-08-06  6:00     ` Shengjiu Wang
2025-08-06  7:54       ` Liu Ying
2025-08-05 14:50   ` kernel test robot
2025-08-04 10:47 ` [PATCH v3 6/6] arm64: dts: imx8mp: Add hdmi parallel audio interface node Shengjiu Wang
2025-08-05  7:10   ` Alexander Stein
2025-08-06  3:49     ` Shengjiu Wang

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to='CAA+D8AN3VzFx1g=8wyxJROw96xS2-qoVs3X4vUfFnJtUCqFj_w@mail.gmail.com' \
    --to=shengjiu.wang@gmail.com \
    --cc=Laurent.pinchart@ideasonboard.com \
    --cc=airlied@gmail.com \
    --cc=andrzej.hajda@intel.com \
    --cc=conor+dt@kernel.org \
    --cc=cristian.ciocaltea@collabora.com \
    --cc=devicetree@vger.kernel.org \
    --cc=dianders@chromium.org \
    --cc=dri-devel@lists.freedesktop.org \
    --cc=festevam@gmail.com \
    --cc=imx@lists.linux.dev \
    --cc=jernej.skrabec@gmail.com \
    --cc=jonas@kwiboo.se \
    --cc=kernel@pengutronix.de \
    --cc=krzk+dt@kernel.org \
    --cc=l.stach@pengutronix.de \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-sound@vger.kernel.org \
    --cc=luca.ceresoli@bootlin.com \
    --cc=lumag@kernel.org \
    --cc=maarten.lankhorst@linux.intel.com \
    --cc=mripard@kernel.org \
    --cc=neil.armstrong@linaro.org \
    --cc=p.zabel@pengutronix.de \
    --cc=perex@perex.cz \
    --cc=rfoss@kernel.org \
    --cc=robh@kernel.org \
    --cc=s.hauer@pengutronix.de \
    --cc=shawnguo@kernel.org \
    --cc=shengjiu.wang@nxp.com \
    --cc=simona@ffwll.ch \
    --cc=tiwai@suse.com \
    --cc=tzimmermann@suse.de \
    --cc=victor.liu@nxp.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).