提交 52b50ae1 编写于 作者: D Dave Airlie

Merge tag 'drm-misc-next-fixes-2018-10-31' of...

Merge tag 'drm-misc-next-fixes-2018-10-31' of git://anongit.freedesktop.org/drm/drm-misc into drm-next

- Properly label Innolux TV123WAM as P120ZDG-BF1 (Doug)
- Add optional delay for panels without hpd hooked up (which solves the
  mystery delay for TI SN65DSI86 bridge) (Doug)
- Another 6bpc quirk for BOE panel 0x0771 (Shawn)

Cc: Doug Anderson <dianders@chromium.org>
Cc: Lee, Shawn C <shawn.c.lee@intel.com>
Signed-off-by: NDave Airlie <airlied@redhat.com>

From: Sean Paul <sean@poorly.run>
Link: https://patchwork.freedesktop.org/patch/msgid/20181031201944.GA262020@art_vandelay
Innolux TV123WAM 12.3 inch eDP 2K display panel Innolux P120ZDG-BF1 12.02 inch eDP 2K display panel
This binding is compatible with the simple-panel binding, which is specified This binding is compatible with the simple-panel binding, which is specified
in simple-panel.txt in this directory. in simple-panel.txt in this directory.
Required properties: Required properties:
- compatible: should be "innolux,tv123wam" - compatible: should be "innolux,p120zdg-bf1"
- power-supply: regulator to provide the supply voltage - power-supply: regulator to provide the supply voltage
Optional properties: Optional properties:
- enable-gpios: GPIO pin to enable or disable the panel - enable-gpios: GPIO pin to enable or disable the panel
- backlight: phandle of the backlight device attached to the panel - backlight: phandle of the backlight device attached to the panel
- no-hpd: If HPD isn't hooked up; add this property.
Example: Example:
panel_edp: panel-edp { panel_edp: panel-edp {
compatible = "innolux,tv123wam"; compatible = "innolux,p120zdg-bf1";
enable-gpios = <&msmgpio 31 GPIO_ACTIVE_LOW>; enable-gpios = <&msmgpio 31 GPIO_ACTIVE_LOW>;
power-supply = <&pm8916_l2>; power-supply = <&pm8916_l2>;
backlight = <&backlight>; backlight = <&backlight>;
no-hpd;
}; };
...@@ -11,6 +11,9 @@ Optional properties: ...@@ -11,6 +11,9 @@ Optional properties:
- ddc-i2c-bus: phandle of an I2C controller used for DDC EDID probing - ddc-i2c-bus: phandle of an I2C controller used for DDC EDID probing
- enable-gpios: GPIO pin to enable or disable the panel - enable-gpios: GPIO pin to enable or disable the panel
- backlight: phandle of the backlight device attached to the panel - backlight: phandle of the backlight device attached to the panel
- no-hpd: This panel is supposed to communicate that it's ready via HPD
(hot plug detect) signal, but the signal isn't hooked up so we should
hardcode the max delay from the panel spec when powering up the panel.
Example: Example:
......
...@@ -458,18 +458,6 @@ static void ti_sn_bridge_enable(struct drm_bridge *bridge) ...@@ -458,18 +458,6 @@ static void ti_sn_bridge_enable(struct drm_bridge *bridge)
unsigned int val; unsigned int val;
int ret; int ret;
/*
* FIXME:
* This 70ms was found necessary by experimentation. If it's not
* present, link training fails. It seems like it can go anywhere from
* pre_enable() up to semi-auto link training initiation below.
*
* Neither the datasheet for the bridge nor the panel tested mention a
* delay of this magnitude in the timing requirements. So for now, add
* the mystery delay until someone figures out a better fix.
*/
msleep(70);
/* DSI_A lane config */ /* DSI_A lane config */
val = CHA_DSI_LANES(4 - pdata->dsi->lanes); val = CHA_DSI_LANES(4 - pdata->dsi->lanes);
regmap_update_bits(pdata->regmap, SN_DSI_LANES_REG, regmap_update_bits(pdata->regmap, SN_DSI_LANES_REG,
...@@ -536,7 +524,22 @@ static void ti_sn_bridge_pre_enable(struct drm_bridge *bridge) ...@@ -536,7 +524,22 @@ static void ti_sn_bridge_pre_enable(struct drm_bridge *bridge)
/* configure bridge ref_clk */ /* configure bridge ref_clk */
ti_sn_bridge_set_refclk_freq(pdata); ti_sn_bridge_set_refclk_freq(pdata);
/* in case drm_panel is connected then HPD is not supported */ /*
* HPD on this bridge chip is a bit useless. This is an eDP bridge
* so the HPD is an internal signal that's only there to signal that
* the panel is done powering up. ...but the bridge chip debounces
* this signal by between 100 ms and 400 ms (depending on process,
* voltage, and temperate--I measured it at about 200 ms). One
* particular panel asserted HPD 84 ms after it was powered on meaning
* that we saw HPD 284 ms after power on. ...but the same panel said
* that instead of looking at HPD you could just hardcode a delay of
* 200 ms. We'll assume that the panel driver will have the hardcoded
* delay in its prepare and always disable HPD.
*
* If HPD somehow makes sense on some future panel we'll have to
* change this to be conditional on someone specifying that HPD should
* be used.
*/
regmap_update_bits(pdata->regmap, SN_HPD_DISABLE_REG, HPD_DISABLE, regmap_update_bits(pdata->regmap, SN_HPD_DISABLE_REG, HPD_DISABLE,
HPD_DISABLE); HPD_DISABLE);
......
...@@ -119,6 +119,9 @@ static const struct edid_quirk { ...@@ -119,6 +119,9 @@ static const struct edid_quirk {
/* SDC panel of Lenovo B50-80 reports 8 bpc, but is a 6 bpc panel */ /* SDC panel of Lenovo B50-80 reports 8 bpc, but is a 6 bpc panel */
{ "SDC", 0x3652, EDID_QUIRK_FORCE_6BPC }, { "SDC", 0x3652, EDID_QUIRK_FORCE_6BPC },
/* BOE model 0x0771 reports 8 bpc, but is a 6 bpc panel */
{ "BOE", 0x0771, EDID_QUIRK_FORCE_6BPC },
/* Belinea 10 15 55 */ /* Belinea 10 15 55 */
{ "MAX", 1516, EDID_QUIRK_PREFER_LARGE_60 }, { "MAX", 1516, EDID_QUIRK_PREFER_LARGE_60 },
{ "MAX", 0x77e, EDID_QUIRK_PREFER_LARGE_60 }, { "MAX", 0x77e, EDID_QUIRK_PREFER_LARGE_60 },
......
...@@ -56,6 +56,8 @@ struct panel_desc { ...@@ -56,6 +56,8 @@ struct panel_desc {
/** /**
* @prepare: the time (in milliseconds) that it takes for the panel to * @prepare: the time (in milliseconds) that it takes for the panel to
* become ready and start receiving video data * become ready and start receiving video data
* @hpd_absent_delay: Add this to the prepare delay if we know Hot
* Plug Detect isn't used.
* @enable: the time (in milliseconds) that it takes for the panel to * @enable: the time (in milliseconds) that it takes for the panel to
* display the first valid frame after starting to receive * display the first valid frame after starting to receive
* video data * video data
...@@ -66,6 +68,7 @@ struct panel_desc { ...@@ -66,6 +68,7 @@ struct panel_desc {
*/ */
struct { struct {
unsigned int prepare; unsigned int prepare;
unsigned int hpd_absent_delay;
unsigned int enable; unsigned int enable;
unsigned int disable; unsigned int disable;
unsigned int unprepare; unsigned int unprepare;
...@@ -79,6 +82,7 @@ struct panel_simple { ...@@ -79,6 +82,7 @@ struct panel_simple {
struct drm_panel base; struct drm_panel base;
bool prepared; bool prepared;
bool enabled; bool enabled;
bool no_hpd;
const struct panel_desc *desc; const struct panel_desc *desc;
...@@ -202,6 +206,7 @@ static int panel_simple_unprepare(struct drm_panel *panel) ...@@ -202,6 +206,7 @@ static int panel_simple_unprepare(struct drm_panel *panel)
static int panel_simple_prepare(struct drm_panel *panel) static int panel_simple_prepare(struct drm_panel *panel)
{ {
struct panel_simple *p = to_panel_simple(panel); struct panel_simple *p = to_panel_simple(panel);
unsigned int delay;
int err; int err;
if (p->prepared) if (p->prepared)
...@@ -215,8 +220,11 @@ static int panel_simple_prepare(struct drm_panel *panel) ...@@ -215,8 +220,11 @@ static int panel_simple_prepare(struct drm_panel *panel)
gpiod_set_value_cansleep(p->enable_gpio, 1); gpiod_set_value_cansleep(p->enable_gpio, 1);
if (p->desc->delay.prepare) delay = p->desc->delay.prepare;
msleep(p->desc->delay.prepare); if (p->no_hpd)
delay += p->desc->delay.hpd_absent_delay;
if (delay)
msleep(delay);
p->prepared = true; p->prepared = true;
...@@ -305,6 +313,8 @@ static int panel_simple_probe(struct device *dev, const struct panel_desc *desc) ...@@ -305,6 +313,8 @@ static int panel_simple_probe(struct device *dev, const struct panel_desc *desc)
panel->prepared = false; panel->prepared = false;
panel->desc = desc; panel->desc = desc;
panel->no_hpd = of_property_read_bool(dev->of_node, "no-hpd");
panel->supply = devm_regulator_get(dev, "power"); panel->supply = devm_regulator_get(dev, "power");
if (IS_ERR(panel->supply)) if (IS_ERR(panel->supply))
return PTR_ERR(panel->supply); return PTR_ERR(panel->supply);
...@@ -1363,7 +1373,7 @@ static const struct panel_desc innolux_n156bge_l21 = { ...@@ -1363,7 +1373,7 @@ static const struct panel_desc innolux_n156bge_l21 = {
}, },
}; };
static const struct drm_display_mode innolux_tv123wam_mode = { static const struct drm_display_mode innolux_p120zdg_bf1_mode = {
.clock = 206016, .clock = 206016,
.hdisplay = 2160, .hdisplay = 2160,
.hsync_start = 2160 + 48, .hsync_start = 2160 + 48,
...@@ -1377,15 +1387,16 @@ static const struct drm_display_mode innolux_tv123wam_mode = { ...@@ -1377,15 +1387,16 @@ static const struct drm_display_mode innolux_tv123wam_mode = {
.flags = DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC, .flags = DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC,
}; };
static const struct panel_desc innolux_tv123wam = { static const struct panel_desc innolux_p120zdg_bf1 = {
.modes = &innolux_tv123wam_mode, .modes = &innolux_p120zdg_bf1_mode,
.num_modes = 1, .num_modes = 1,
.bpc = 8, .bpc = 8,
.size = { .size = {
.width = 259, .width = 254,
.height = 173, .height = 169,
}, },
.delay = { .delay = {
.hpd_absent_delay = 200,
.unprepare = 500, .unprepare = 500,
}, },
}; };
...@@ -2445,8 +2456,8 @@ static const struct of_device_id platform_of_match[] = { ...@@ -2445,8 +2456,8 @@ static const struct of_device_id platform_of_match[] = {
.compatible = "innolux,n156bge-l21", .compatible = "innolux,n156bge-l21",
.data = &innolux_n156bge_l21, .data = &innolux_n156bge_l21,
}, { }, {
.compatible = "innolux,tv123wam", .compatible = "innolux,p120zdg-bf1",
.data = &innolux_tv123wam, .data = &innolux_p120zdg_bf1,
}, { }, {
.compatible = "innolux,zj070na-01p", .compatible = "innolux,zj070na-01p",
.data = &innolux_zj070na_01p, .data = &innolux_zj070na_01p,
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册