提交 7b74026d 编写于 作者: D Dave Airlie

Merge tag 'drm-misc-fixes-2018-11-14' of git://anongit.freedesktop.org/drm/drm-misc into drm-fixes

Cross-subsystem:
- omap: Instantiate dss children in omapdss instead of mach (Laurent)

Other:
- htmldocs build warning (Sean)
- MST NULL deref fix (Stanislav)
- omap: Various runtime ref gets on probe/bind (Laurent)
- omap: Fix to the above dss children patch (Tony)

Cc: Sean Paul <sean@poorly.run>
Cc: Stanislav Lisovskiy <stanislav.lisovskiy@intel.com>
Cc: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Cc: Tony Lindgren <tony@atomide.com>
Signed-off-by: NDave Airlie <airlied@redhat.com>
From: Sean Paul <sean@poorly.run>
Link: https://patchwork.freedesktop.org/patch/msgid/20181114204542.GA52569@art_vandelay
...@@ -209,11 +209,61 @@ static int __init omapdss_init_fbdev(void) ...@@ -209,11 +209,61 @@ static int __init omapdss_init_fbdev(void)
return 0; return 0;
} }
#else
static inline int omapdss_init_fbdev(void) static const char * const omapdss_compat_names[] __initconst = {
"ti,omap2-dss",
"ti,omap3-dss",
"ti,omap4-dss",
"ti,omap5-dss",
"ti,dra7-dss",
};
static struct device_node * __init omapdss_find_dss_of_node(void)
{ {
return 0; struct device_node *node;
int i;
for (i = 0; i < ARRAY_SIZE(omapdss_compat_names); ++i) {
node = of_find_compatible_node(NULL, NULL,
omapdss_compat_names[i]);
if (node)
return node;
}
return NULL;
} }
static int __init omapdss_init_of(void)
{
int r;
struct device_node *node;
struct platform_device *pdev;
/* only create dss helper devices if dss is enabled in the .dts */
node = omapdss_find_dss_of_node();
if (!node)
return 0;
if (!of_device_is_available(node))
return 0;
pdev = of_find_device_by_node(node);
if (!pdev) {
pr_err("Unable to find DSS platform device\n");
return -ENODEV;
}
r = of_platform_populate(node, NULL, NULL, &pdev->dev);
if (r) {
pr_err("Unable to populate DSS submodule devices\n");
return r;
}
return omapdss_init_fbdev();
}
omap_device_initcall(omapdss_init_of);
#endif /* CONFIG_FB_OMAP2 */ #endif /* CONFIG_FB_OMAP2 */
static void dispc_disable_outputs(void) static void dispc_disable_outputs(void)
...@@ -361,58 +411,3 @@ int omap_dss_reset(struct omap_hwmod *oh) ...@@ -361,58 +411,3 @@ int omap_dss_reset(struct omap_hwmod *oh)
return r; return r;
} }
static const char * const omapdss_compat_names[] __initconst = {
"ti,omap2-dss",
"ti,omap3-dss",
"ti,omap4-dss",
"ti,omap5-dss",
"ti,dra7-dss",
};
static struct device_node * __init omapdss_find_dss_of_node(void)
{
struct device_node *node;
int i;
for (i = 0; i < ARRAY_SIZE(omapdss_compat_names); ++i) {
node = of_find_compatible_node(NULL, NULL,
omapdss_compat_names[i]);
if (node)
return node;
}
return NULL;
}
static int __init omapdss_init_of(void)
{
int r;
struct device_node *node;
struct platform_device *pdev;
/* only create dss helper devices if dss is enabled in the .dts */
node = omapdss_find_dss_of_node();
if (!node)
return 0;
if (!of_device_is_available(node))
return 0;
pdev = of_find_device_by_node(node);
if (!pdev) {
pr_err("Unable to find DSS platform device\n");
return -ENODEV;
}
r = of_platform_populate(node, NULL, NULL, &pdev->dev);
if (r) {
pr_err("Unable to populate DSS submodule devices\n");
return r;
}
return omapdss_init_fbdev();
}
omap_device_initcall(omapdss_init_of);
...@@ -1275,6 +1275,9 @@ static struct drm_dp_mst_branch *drm_dp_get_mst_branch_device(struct drm_dp_mst_ ...@@ -1275,6 +1275,9 @@ static struct drm_dp_mst_branch *drm_dp_get_mst_branch_device(struct drm_dp_mst_
mutex_lock(&mgr->lock); mutex_lock(&mgr->lock);
mstb = mgr->mst_primary; mstb = mgr->mst_primary;
if (!mstb)
goto out;
for (i = 0; i < lct - 1; i++) { for (i = 0; i < lct - 1; i++) {
int shift = (i % 2) ? 0 : 4; int shift = (i % 2) ? 0 : 4;
int port_num = (rad[i / 2] >> shift) & 0xf; int port_num = (rad[i / 2] >> shift) & 0xf;
......
...@@ -97,9 +97,9 @@ EXPORT_SYMBOL(drm_mode_legacy_fb_format); ...@@ -97,9 +97,9 @@ EXPORT_SYMBOL(drm_mode_legacy_fb_format);
/** /**
* drm_driver_legacy_fb_format - compute drm fourcc code from legacy description * drm_driver_legacy_fb_format - compute drm fourcc code from legacy description
* @dev: DRM device
* @bpp: bits per pixels * @bpp: bits per pixels
* @depth: bit depth per pixel * @depth: bit depth per pixel
* @native: use host native byte order
* *
* Computes a drm fourcc pixel format code for the given @bpp/@depth values. * Computes a drm fourcc pixel format code for the given @bpp/@depth values.
* Unlike drm_mode_legacy_fb_format() this looks at the drivers mode_config, * Unlike drm_mode_legacy_fb_format() this looks at the drivers mode_config,
......
...@@ -854,6 +854,13 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, ...@@ -854,6 +854,13 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic,
unsigned int sof_lines; unsigned int sof_lines;
unsigned int vsync_lines; unsigned int vsync_lines;
/* Use VENCI for 480i and 576i and double HDMI pixels */
if (mode->flags & DRM_MODE_FLAG_DBLCLK) {
hdmi_repeat = true;
use_enci = true;
venc_hdmi_latency = 1;
}
if (meson_venc_hdmi_supported_vic(vic)) { if (meson_venc_hdmi_supported_vic(vic)) {
vmode = meson_venc_hdmi_get_vic_vmode(vic); vmode = meson_venc_hdmi_get_vic_vmode(vic);
if (!vmode) { if (!vmode) {
...@@ -865,13 +872,7 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, ...@@ -865,13 +872,7 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic,
} else { } else {
meson_venc_hdmi_get_dmt_vmode(mode, &vmode_dmt); meson_venc_hdmi_get_dmt_vmode(mode, &vmode_dmt);
vmode = &vmode_dmt; vmode = &vmode_dmt;
} use_enci = false;
/* Use VENCI for 480i and 576i and double HDMI pixels */
if (mode->flags & DRM_MODE_FLAG_DBLCLK) {
hdmi_repeat = true;
use_enci = true;
venc_hdmi_latency = 1;
} }
/* Repeat VENC pixels for 480/576i/p, 720p50/60 and 1080p50/60 */ /* Repeat VENC pixels for 480/576i/p, 720p50/60 and 1080p50/60 */
......
...@@ -5409,11 +5409,14 @@ static int dsi_probe(struct platform_device *pdev) ...@@ -5409,11 +5409,14 @@ static int dsi_probe(struct platform_device *pdev)
/* DSI on OMAP3 doesn't have register DSI_GNQ, set number /* DSI on OMAP3 doesn't have register DSI_GNQ, set number
* of data to 3 by default */ * of data to 3 by default */
if (dsi->data->quirks & DSI_QUIRK_GNQ) if (dsi->data->quirks & DSI_QUIRK_GNQ) {
dsi_runtime_get(dsi);
/* NB_DATA_LANES */ /* NB_DATA_LANES */
dsi->num_lanes_supported = 1 + REG_GET(dsi, DSI_GNQ, 11, 9); dsi->num_lanes_supported = 1 + REG_GET(dsi, DSI_GNQ, 11, 9);
else dsi_runtime_put(dsi);
} else {
dsi->num_lanes_supported = 3; dsi->num_lanes_supported = 3;
}
r = dsi_init_output(dsi); r = dsi_init_output(dsi);
if (r) if (r)
...@@ -5426,15 +5429,19 @@ static int dsi_probe(struct platform_device *pdev) ...@@ -5426,15 +5429,19 @@ static int dsi_probe(struct platform_device *pdev)
} }
r = of_platform_populate(dev->of_node, NULL, NULL, dev); r = of_platform_populate(dev->of_node, NULL, NULL, dev);
if (r) if (r) {
DSSERR("Failed to populate DSI child devices: %d\n", r); DSSERR("Failed to populate DSI child devices: %d\n", r);
goto err_uninit_output;
}
r = component_add(&pdev->dev, &dsi_component_ops); r = component_add(&pdev->dev, &dsi_component_ops);
if (r) if (r)
goto err_uninit_output; goto err_of_depopulate;
return 0; return 0;
err_of_depopulate:
of_platform_depopulate(dev);
err_uninit_output: err_uninit_output:
dsi_uninit_output(dsi); dsi_uninit_output(dsi);
err_pm_disable: err_pm_disable:
...@@ -5470,19 +5477,12 @@ static int dsi_runtime_suspend(struct device *dev) ...@@ -5470,19 +5477,12 @@ static int dsi_runtime_suspend(struct device *dev)
/* wait for current handler to finish before turning the DSI off */ /* wait for current handler to finish before turning the DSI off */
synchronize_irq(dsi->irq); synchronize_irq(dsi->irq);
dispc_runtime_put(dsi->dss->dispc);
return 0; return 0;
} }
static int dsi_runtime_resume(struct device *dev) static int dsi_runtime_resume(struct device *dev)
{ {
struct dsi_data *dsi = dev_get_drvdata(dev); struct dsi_data *dsi = dev_get_drvdata(dev);
int r;
r = dispc_runtime_get(dsi->dss->dispc);
if (r)
return r;
dsi->is_enabled = true; dsi->is_enabled = true;
/* ensure the irq handler sees the is_enabled value */ /* ensure the irq handler sees the is_enabled value */
......
...@@ -1484,16 +1484,23 @@ static int dss_probe(struct platform_device *pdev) ...@@ -1484,16 +1484,23 @@ static int dss_probe(struct platform_device *pdev)
dss); dss);
/* Add all the child devices as components. */ /* Add all the child devices as components. */
r = of_platform_populate(pdev->dev.of_node, NULL, NULL, &pdev->dev);
if (r)
goto err_uninit_debugfs;
omapdss_gather_components(&pdev->dev); omapdss_gather_components(&pdev->dev);
device_for_each_child(&pdev->dev, &match, dss_add_child_component); device_for_each_child(&pdev->dev, &match, dss_add_child_component);
r = component_master_add_with_match(&pdev->dev, &dss_component_ops, match); r = component_master_add_with_match(&pdev->dev, &dss_component_ops, match);
if (r) if (r)
goto err_uninit_debugfs; goto err_of_depopulate;
return 0; return 0;
err_of_depopulate:
of_platform_depopulate(&pdev->dev);
err_uninit_debugfs: err_uninit_debugfs:
dss_debugfs_remove_file(dss->debugfs.clk); dss_debugfs_remove_file(dss->debugfs.clk);
dss_debugfs_remove_file(dss->debugfs.dss); dss_debugfs_remove_file(dss->debugfs.dss);
...@@ -1522,6 +1529,8 @@ static int dss_remove(struct platform_device *pdev) ...@@ -1522,6 +1529,8 @@ static int dss_remove(struct platform_device *pdev)
{ {
struct dss_device *dss = platform_get_drvdata(pdev); struct dss_device *dss = platform_get_drvdata(pdev);
of_platform_depopulate(&pdev->dev);
component_master_del(&pdev->dev, &dss_component_ops); component_master_del(&pdev->dev, &dss_component_ops);
dss_debugfs_remove_file(dss->debugfs.clk); dss_debugfs_remove_file(dss->debugfs.clk);
......
...@@ -635,10 +635,14 @@ static int hdmi4_bind(struct device *dev, struct device *master, void *data) ...@@ -635,10 +635,14 @@ static int hdmi4_bind(struct device *dev, struct device *master, void *data)
hdmi->dss = dss; hdmi->dss = dss;
r = hdmi_pll_init(dss, hdmi->pdev, &hdmi->pll, &hdmi->wp); r = hdmi_runtime_get(hdmi);
if (r) if (r)
return r; return r;
r = hdmi_pll_init(dss, hdmi->pdev, &hdmi->pll, &hdmi->wp);
if (r)
goto err_runtime_put;
r = hdmi4_cec_init(hdmi->pdev, &hdmi->core, &hdmi->wp); r = hdmi4_cec_init(hdmi->pdev, &hdmi->core, &hdmi->wp);
if (r) if (r)
goto err_pll_uninit; goto err_pll_uninit;
...@@ -652,12 +656,16 @@ static int hdmi4_bind(struct device *dev, struct device *master, void *data) ...@@ -652,12 +656,16 @@ static int hdmi4_bind(struct device *dev, struct device *master, void *data)
hdmi->debugfs = dss_debugfs_create_file(dss, "hdmi", hdmi_dump_regs, hdmi->debugfs = dss_debugfs_create_file(dss, "hdmi", hdmi_dump_regs,
hdmi); hdmi);
hdmi_runtime_put(hdmi);
return 0; return 0;
err_cec_uninit: err_cec_uninit:
hdmi4_cec_uninit(&hdmi->core); hdmi4_cec_uninit(&hdmi->core);
err_pll_uninit: err_pll_uninit:
hdmi_pll_uninit(&hdmi->pll); hdmi_pll_uninit(&hdmi->pll);
err_runtime_put:
hdmi_runtime_put(hdmi);
return r; return r;
} }
...@@ -833,32 +841,6 @@ static int hdmi4_remove(struct platform_device *pdev) ...@@ -833,32 +841,6 @@ static int hdmi4_remove(struct platform_device *pdev)
return 0; return 0;
} }
static int hdmi_runtime_suspend(struct device *dev)
{
struct omap_hdmi *hdmi = dev_get_drvdata(dev);
dispc_runtime_put(hdmi->dss->dispc);
return 0;
}
static int hdmi_runtime_resume(struct device *dev)
{
struct omap_hdmi *hdmi = dev_get_drvdata(dev);
int r;
r = dispc_runtime_get(hdmi->dss->dispc);
if (r < 0)
return r;
return 0;
}
static const struct dev_pm_ops hdmi_pm_ops = {
.runtime_suspend = hdmi_runtime_suspend,
.runtime_resume = hdmi_runtime_resume,
};
static const struct of_device_id hdmi_of_match[] = { static const struct of_device_id hdmi_of_match[] = {
{ .compatible = "ti,omap4-hdmi", }, { .compatible = "ti,omap4-hdmi", },
{}, {},
...@@ -869,7 +851,6 @@ struct platform_driver omapdss_hdmi4hw_driver = { ...@@ -869,7 +851,6 @@ struct platform_driver omapdss_hdmi4hw_driver = {
.remove = hdmi4_remove, .remove = hdmi4_remove,
.driver = { .driver = {
.name = "omapdss_hdmi", .name = "omapdss_hdmi",
.pm = &hdmi_pm_ops,
.of_match_table = hdmi_of_match, .of_match_table = hdmi_of_match,
.suppress_bind_attrs = true, .suppress_bind_attrs = true,
}, },
......
...@@ -825,32 +825,6 @@ static int hdmi5_remove(struct platform_device *pdev) ...@@ -825,32 +825,6 @@ static int hdmi5_remove(struct platform_device *pdev)
return 0; return 0;
} }
static int hdmi_runtime_suspend(struct device *dev)
{
struct omap_hdmi *hdmi = dev_get_drvdata(dev);
dispc_runtime_put(hdmi->dss->dispc);
return 0;
}
static int hdmi_runtime_resume(struct device *dev)
{
struct omap_hdmi *hdmi = dev_get_drvdata(dev);
int r;
r = dispc_runtime_get(hdmi->dss->dispc);
if (r < 0)
return r;
return 0;
}
static const struct dev_pm_ops hdmi_pm_ops = {
.runtime_suspend = hdmi_runtime_suspend,
.runtime_resume = hdmi_runtime_resume,
};
static const struct of_device_id hdmi_of_match[] = { static const struct of_device_id hdmi_of_match[] = {
{ .compatible = "ti,omap5-hdmi", }, { .compatible = "ti,omap5-hdmi", },
{ .compatible = "ti,dra7-hdmi", }, { .compatible = "ti,dra7-hdmi", },
...@@ -862,7 +836,6 @@ struct platform_driver omapdss_hdmi5hw_driver = { ...@@ -862,7 +836,6 @@ struct platform_driver omapdss_hdmi5hw_driver = {
.remove = hdmi5_remove, .remove = hdmi5_remove,
.driver = { .driver = {
.name = "omapdss_hdmi5", .name = "omapdss_hdmi5",
.pm = &hdmi_pm_ops,
.of_match_table = hdmi_of_match, .of_match_table = hdmi_of_match,
.suppress_bind_attrs = true, .suppress_bind_attrs = true,
}, },
......
...@@ -946,19 +946,12 @@ static int venc_runtime_suspend(struct device *dev) ...@@ -946,19 +946,12 @@ static int venc_runtime_suspend(struct device *dev)
if (venc->tv_dac_clk) if (venc->tv_dac_clk)
clk_disable_unprepare(venc->tv_dac_clk); clk_disable_unprepare(venc->tv_dac_clk);
dispc_runtime_put(venc->dss->dispc);
return 0; return 0;
} }
static int venc_runtime_resume(struct device *dev) static int venc_runtime_resume(struct device *dev)
{ {
struct venc_device *venc = dev_get_drvdata(dev); struct venc_device *venc = dev_get_drvdata(dev);
int r;
r = dispc_runtime_get(venc->dss->dispc);
if (r < 0)
return r;
if (venc->tv_dac_clk) if (venc->tv_dac_clk)
clk_prepare_enable(venc->tv_dac_clk); clk_prepare_enable(venc->tv_dac_clk);
......
...@@ -350,11 +350,14 @@ static void omap_crtc_arm_event(struct drm_crtc *crtc) ...@@ -350,11 +350,14 @@ static void omap_crtc_arm_event(struct drm_crtc *crtc)
static void omap_crtc_atomic_enable(struct drm_crtc *crtc, static void omap_crtc_atomic_enable(struct drm_crtc *crtc,
struct drm_crtc_state *old_state) struct drm_crtc_state *old_state)
{ {
struct omap_drm_private *priv = crtc->dev->dev_private;
struct omap_crtc *omap_crtc = to_omap_crtc(crtc); struct omap_crtc *omap_crtc = to_omap_crtc(crtc);
int ret; int ret;
DBG("%s", omap_crtc->name); DBG("%s", omap_crtc->name);
priv->dispc_ops->runtime_get(priv->dispc);
spin_lock_irq(&crtc->dev->event_lock); spin_lock_irq(&crtc->dev->event_lock);
drm_crtc_vblank_on(crtc); drm_crtc_vblank_on(crtc);
ret = drm_crtc_vblank_get(crtc); ret = drm_crtc_vblank_get(crtc);
...@@ -367,6 +370,7 @@ static void omap_crtc_atomic_enable(struct drm_crtc *crtc, ...@@ -367,6 +370,7 @@ static void omap_crtc_atomic_enable(struct drm_crtc *crtc,
static void omap_crtc_atomic_disable(struct drm_crtc *crtc, static void omap_crtc_atomic_disable(struct drm_crtc *crtc,
struct drm_crtc_state *old_state) struct drm_crtc_state *old_state)
{ {
struct omap_drm_private *priv = crtc->dev->dev_private;
struct omap_crtc *omap_crtc = to_omap_crtc(crtc); struct omap_crtc *omap_crtc = to_omap_crtc(crtc);
DBG("%s", omap_crtc->name); DBG("%s", omap_crtc->name);
...@@ -379,6 +383,8 @@ static void omap_crtc_atomic_disable(struct drm_crtc *crtc, ...@@ -379,6 +383,8 @@ static void omap_crtc_atomic_disable(struct drm_crtc *crtc,
spin_unlock_irq(&crtc->dev->event_lock); spin_unlock_irq(&crtc->dev->event_lock);
drm_crtc_vblank_off(crtc); drm_crtc_vblank_off(crtc);
priv->dispc_ops->runtime_put(priv->dispc);
} }
static enum drm_mode_status omap_crtc_mode_valid(struct drm_crtc *crtc, static enum drm_mode_status omap_crtc_mode_valid(struct drm_crtc *crtc,
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册