All of lore.kernel.org
 help / color / mirror / Atom feed
From: "Sharma, Shashank" <shashank.sharma@intel.com>
To: Rodrigo Vivi <rodrigo.vivi@gmail.com>,
	"Pandiyan, Dhinakaran" <dhinakaran.pandiyan@intel.com>
Cc: intel-gfx <intel-gfx@lists.freedesktop.org>,
	Paulo Zanoni <paulo.r.zanoni@intel.com>
Subject: Re: [PATCH v2 1/4] drm: Helper for lspcon in drm_dp_dual_mode
Date: Fri, 01 Jul 2016 11:28:24 +0530	[thread overview]
Message-ID: <57760680.6050206@intel.com> (raw)
In-Reply-To: <CABVU7+smk=FzCBZGSfMqEvbU6_n6KFi21j_8Syxfjy=trNYxBQ@mail.gmail.com>

Thanks for the review Rodrigo. My comments inline.

Regards
Shashank

On 7/1/2016 3:46 AM, Rodrigo Vivi wrote:
> On Tue, Jun 21, 2016 at 8:00 AM, Shashank Sharma
> <shashank.sharma@intel.com> wrote:
>> This patch adds lspcon support in dp_dual_mode helper.
>> lspcon is essentially a dp->hdmi dongle with dual personality.
>>
>> LS mode: It works as a passive dongle, by level shifting DP++
>> signals to HDMI signals, in LS mode.
>> PCON mode: It works as a protocol converter active dongle
>> in pcon mode, by converting DP++ outputs to HDMI 2.0 outputs.
>>
>> This patch adds support for lspcon detection and mode set
>> switch operations, as a dp dual mode dongle.
>>
>> v2: Addressed review comments from Ville
>> - add adaptor id for lspcon devices (0x08), use it to identify lspcon
>> - change function names
>>    old: drm_lspcon_get_current_mode/drm_lspcon_change_mode
>>    new: drm_lspcon_get_mode/drm_lspcon_set_mode
>> - change drm_lspcon_get_mode type to int, to match
>>    drm_dp_dual_mode_get_tmds_output
>> - change 'err' to 'ret' to match the rest of the functions
>> - remove pointless typecasting during call to dual_mode_read
>> - fix the but while setting value of data, while writing lspcon mode
>> - fix indentation
>> - change mdelay(10) -> msleep(10)
>> - return ETIMEDOUT instead of EFAULT, when lspcon mode change times out
>> - Add an empty line to separate std regs macros and lspcon regs macros
>>    Indent bit definition
>>
>> Signed-off-by: Shashank Sharma <shashank.sharma@intel.com>
>> ---
>>   drivers/gpu/drm/drm_dp_dual_mode_helper.c | 103 ++++++++++++++++++++++++++++++
>>   include/drm/drm_dp_dual_mode_helper.h     |  25 ++++++++
>>   2 files changed, 128 insertions(+)
>>
>> diff --git a/drivers/gpu/drm/drm_dp_dual_mode_helper.c b/drivers/gpu/drm/drm_dp_dual_mode_helper.c
>> index a7b2a75..404e715 100644
>> --- a/drivers/gpu/drm/drm_dp_dual_mode_helper.c
>> +++ b/drivers/gpu/drm/drm_dp_dual_mode_helper.c
>> @@ -148,6 +148,14 @@ static bool is_type2_adaptor(uint8_t adaptor_id)
>>                                DP_DUAL_MODE_REV_TYPE2);
>>   }
>>
>> +bool is_lspcon_adaptor(const char hdmi_id[DP_DUAL_MODE_HDMI_ID_LEN],
>> +       const uint8_t adaptor_id)
>> +{
>> +       return is_hdmi_adaptor(hdmi_id) &&
>> +               (adaptor_id == (DP_DUAL_MODE_REV_TYPE2 |
>
> DP_DUAL_MODE_REV_TYPE2 = 0 so useless here and confusing.
This was a review comment from Ville, on the last patch. I think he 
suggested for the better readability of the code.
>
>> +                       DP_DUAL_MODE_TYPE_TYPE2 | DP_DUAL_MODE_TYPE_LSPCON));
>
> Also this is confusing and took me a while to uderstand that LSPCON is
> the type2 with DPCD
I know, due to LSPCON's dual personality, its complicated to understand. 
I tried to cover some theory, in the cover letter, can add some here too:
LSPCON is a dp->hdmi adapter which can operate in two modes
Passive dongle mode / LS mode: in this mode, it acts as type2 dp dual 
mode adapter (no DPCD readable here)
Active mode / PCON mode: in this mode, it acts as active DP++->HDMI2.0 
protocol convertor dongle, and allows DPCD read/write like a DP++ display.
>
> so my suggestion is to define DP_DUAL_MODE_TYPE_HAS_DPCD (1<<3) with a
> comment this is defined by LSPCON docs since this is not part of VESA
> DP Dual Mode that only defines the Type2 = 0xA0.
>
> so you could use
> TYPE2 | HAS_DPCD = LSPCON.
>
Sure, got it. Will change it like this.
>> +}
>> +
>>   /**
>>    * drm_dp_dual_mode_detect - Identify the DP dual mode adaptor
>>    * @adapter: I2C adapter for the DDC bus
>> @@ -203,6 +211,8 @@ enum drm_dp_dual_mode_type drm_dp_dual_mode_detect(struct i2c_adapter *adapter)
>>          ret = drm_dp_dual_mode_read(adapter, DP_DUAL_MODE_ADAPTOR_ID,
>>                                      &adaptor_id, sizeof(adaptor_id));
>>          if (ret == 0) {
>> +               if (is_lspcon_adaptor(hdmi_id, adaptor_id))
>> +                       return DRM_DP_DUAL_MODE_LSPCON;
>>                  if (is_type2_adaptor(adaptor_id)) {
>>                          if (is_hdmi_adaptor(hdmi_id))
>>                                  return DRM_DP_DUAL_MODE_TYPE2_HDMI;
>> @@ -364,3 +374,96 @@ const char *drm_dp_get_dual_mode_type_name(enum drm_dp_dual_mode_type type)
>>          }
>>   }
>>   EXPORT_SYMBOL(drm_dp_get_dual_mode_type_name);
>> +
>> +/**
>> + * drm_lspcon_get_current_mode: Get LSPCON's current mode of operation by
>> + * by reading offset (0x80, 0x41)
>> + * @i2c_adapter: I2C-over-aux adapter
>> + * @current_mode: out vaiable, current lspcon mode of operation
>> + *
>> + * Returns:
>> + * 0 on success, sets the current_mode value to appropriate mode
>> + * -error on failure
>> + */
>> +int drm_lspcon_get_mode(struct i2c_adapter *adapter,
>> +       enum drm_lspcon_mode *current_mode)
>> +{
>> +       u8 data;
>> +       int ret = 0;
>> +
>> +       if (!current_mode) {
>> +               DRM_ERROR("NULL input\n");
>> +               return -EINVAL;
>> +       }
>> +
>> +       /* Read Status: i2c over aux */
>> +       ret = drm_dp_dual_mode_read(adapter, DP_DUAL_MODE_LSPCON_CURRENT_MODE,
>> +                       (void *)&data, sizeof(data));
>> +       if (ret < 0) {
>> +               DRM_ERROR("LSPCON read(0x80, 0x41) failed\n");
>> +               return -EFAULT;
>> +       }
>
>> +
>> +       if (data & DP_DUAL_MODE_LSPCON_MODE_MASK)
>> +               *current_mode = DRM_LSPCON_MODE_PCON;
>> +       else
>> +               *current_mode = DRM_LSPCON_MODE_LS;
>> +       return 0;
>> +}
>> +EXPORT_SYMBOL(drm_lspcon_get_mode);
>> +
>> +/**
>> + * drm_lspcon_change_mode: Change LSPCON's mode of operation by
>> + * by writing offset (0x80, 0x40)
>> + * @i2c_adapter: I2C-over-aux adapter
>> + * @reqd_mode: required mode of operation
>> + *
>> + * Returns:
>> + * 0 on success, -error on failure/timeout
>> + */
>> +int drm_lspcon_set_mode(struct i2c_adapter *adapter,
>> +       enum drm_lspcon_mode reqd_mode)
>> +{
>> +       u8 data = 0;
>> +       int ret;
>> +       int time_out = 200;
>> +       enum drm_lspcon_mode changed_mode;
>> +
>> +       if (reqd_mode == DRM_LSPCON_MODE_PCON)
>> +               data = DP_DUAL_MODE_LSPCON_MODE_MASK;
>> +
>> +       /* Change mode */
>> +       ret = drm_dp_dual_mode_write(adapter, DP_DUAL_MODE_LSPCON_MODE_CHANGE,
>> +                       &data, sizeof(data));
>> +       if (ret < 0) {
>> +               DRM_ERROR("LSPCON mode change failed\n");
>> +               return ret;
>> +       }
>> +
>> +       /*
>> +         * Confirm mode change by reading the status bit.
>> +         * Sometimes, it takes a while to change the mode,
>> +         * so wait and retry until time out or done.
>> +         */
>> +       do {
>> +               ret = drm_lspcon_get_mode(adapter, &changed_mode);
>> +               if (ret) {
>> +                       DRM_ERROR("cant confirm LSPCON mode change\n");
>> +                       return ret;
>> +               } else {
>> +                       if (changed_mode != reqd_mode) {
>> +                               msleep(10);
>> +                               time_out -= 10;
>> +                       } else {
>> +                               DRM_DEBUG_KMS("LSPCON mode changed to %s\n",
>> +                                       reqd_mode == DRM_LSPCON_MODE_LS ?
>> +                                               "LS" : "PCON");
>> +                               return 0;
>> +                       }
>> +               }
>> +       } while (time_out);
>> +
>> +       DRM_ERROR("LSPCON mode change timed out\n");
>> +       return -ETIMEDOUT;
>> +}
>> +EXPORT_SYMBOL(drm_lspcon_set_mode);
>> diff --git a/include/drm/drm_dp_dual_mode_helper.h b/include/drm/drm_dp_dual_mode_helper.h
>> index e8a9dfd..441c6cb 100644
>> --- a/include/drm/drm_dp_dual_mode_helper.h
>> +++ b/include/drm/drm_dp_dual_mode_helper.h
>> @@ -24,6 +24,7 @@
>>   #define DRM_DP_DUAL_MODE_HELPER_H
>>
>>   #include <linux/types.h>
>> +#include <drm/drm_edid.h>
>>
>>   /*
>>    * Optional for type 1 DVI adaptors
>> @@ -40,6 +41,7 @@
>>   #define  DP_DUAL_MODE_REV_TYPE2 0x00
>>   #define  DP_DUAL_MODE_TYPE_MASK 0xf0
>>   #define  DP_DUAL_MODE_TYPE_TYPE2 0xa0
>> +#define  DP_DUAL_MODE_TYPE_LSPCON 0x08
>>   #define DP_DUAL_MODE_IEEE_OUI 0x11 /* 11-13*/
>>   #define  DP_DUAL_IEEE_OUI_LEN 3
>>   #define DP_DUAL_DEVICE_ID 0x14 /* 14-19 */
>> @@ -55,6 +57,10 @@
>>   #define  DP_DUAL_MODE_CEC_ENABLE 0x01
>>   #define DP_DUAL_MODE_I2C_SPEED_CTRL 0x22
>>
>> +#define DP_DUAL_MODE_LSPCON_MODE_CHANGE                0x40
>> +#define DP_DUAL_MODE_LSPCON_CURRENT_MODE               0x41
>
> Where did you get this from? I haven't seen any offset 80, adress 41
> defined anywhere in any of the docs I have here. What am I missing?
>
This offset was added by MCA after Intel requested them to confirm the 
LSPCON modeset success. Initially they gave us just 0x40, which is to 
request a change in mode from LS->PCON or other way. But we saw many 
times this change was not happening, so Intel requested MCA to have 
another register offset (0x41) to confirm the current LSPCON mode.
I dont have an updated MCA doc on this, but I can arrange if you insist 
on this.
>> +#define  DP_DUAL_MODE_LSPCON_MODE_MASK                 0x1
>
> I don't believe "mask" is a good term here....
>
> probably
> DP_DUAL_MODE_LSPCON_MODE_PCON (1<<0)
Agree, will change it to something as you suggested

Shashank
>
>> +
>>   struct i2c_adapter;
>>
>>   ssize_t drm_dp_dual_mode_read(struct i2c_adapter *adapter,
>> @@ -63,6 +69,19 @@ ssize_t drm_dp_dual_mode_write(struct i2c_adapter *adapter,
>>                                 u8 offset, const void *buffer, size_t size);
>>
>>   /**
>> +* enum drm_lspcon_mode
>> +* @lspcon_mode_ls: Level shifter mode of LSPCON
>> +*      which drives DP++ to HDMI 1.4 conversion.
>> +* @lspcon_mode_pcon: Protocol converter mode of LSPCON
>> +*      which drives DP++ to HDMI 2.0 active conversion.
>> +*/
>> +enum drm_lspcon_mode {
>> +       DRM_LSPCON_MODE_INVALID,
>> +       DRM_LSPCON_MODE_LS,
>> +       DRM_LSPCON_MODE_PCON,
>> +};
>> +
>> +/**
>>    * enum drm_dp_dual_mode_type - Type of the DP dual mode adaptor
>>    * @DRM_DP_DUAL_MODE_NONE: No DP dual mode adaptor
>>    * @DRM_DP_DUAL_MODE_UNKNOWN: Could be either none or type 1 DVI adaptor
>> @@ -70,6 +89,7 @@ ssize_t drm_dp_dual_mode_write(struct i2c_adapter *adapter,
>>    * @DRM_DP_DUAL_MODE_TYPE1_HDMI: Type 1 HDMI adaptor
>>    * @DRM_DP_DUAL_MODE_TYPE2_DVI: Type 2 DVI adaptor
>>    * @DRM_DP_DUAL_MODE_TYPE2_HDMI: Type 2 HDMI adaptor
>> + * @DRM_DP_DUAL_MODE_TYPE2_LSPCON: Level shifter /protocol converter
>>    */
>>   enum drm_dp_dual_mode_type {
>>          DRM_DP_DUAL_MODE_NONE,
>> @@ -78,6 +98,7 @@ enum drm_dp_dual_mode_type {
>>          DRM_DP_DUAL_MODE_TYPE1_HDMI,
>>          DRM_DP_DUAL_MODE_TYPE2_DVI,
>>          DRM_DP_DUAL_MODE_TYPE2_HDMI,
>> +       DRM_DP_DUAL_MODE_LSPCON,
>>   };
>>
>>   enum drm_dp_dual_mode_type drm_dp_dual_mode_detect(struct i2c_adapter *adapter);
>> @@ -89,4 +110,8 @@ int drm_dp_dual_mode_set_tmds_output(enum drm_dp_dual_mode_type type,
>>                                       struct i2c_adapter *adapter, bool enable);
>>   const char *drm_dp_get_dual_mode_type_name(enum drm_dp_dual_mode_type type);
>>
>> +int drm_lspcon_get_mode(struct i2c_adapter *adapter,
>> +       enum drm_lspcon_mode *current_mode);
>> +int drm_lspcon_set_mode(struct i2c_adapter *adapter,
>> +               enum drm_lspcon_mode reqd_mode);
>>   #endif
>> --
>> 1.9.1
>>
>> _______________________________________________
>> Intel-gfx mailing list
>> Intel-gfx@lists.freedesktop.org
>> https://lists.freedesktop.org/mailman/listinfo/intel-gfx
>
>
>
_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

  reply	other threads:[~2016-07-01  5:58 UTC|newest]

Thread overview: 17+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2016-06-21 15:00 [PATCH v2 0/4] Enable lspcon support for GEN9 devices Shashank Sharma
2016-06-21 15:00 ` [PATCH v2 1/4] drm: Helper for lspcon in drm_dp_dual_mode Shashank Sharma
2016-06-30 22:16   ` Rodrigo Vivi
2016-07-01  5:58     ` Sharma, Shashank [this message]
2016-07-01 14:11       ` Rodrigo Vivi
2016-06-21 15:00 ` [PATCH v2 2/4] drm/i915: Add lspcon support for I915 driver Shashank Sharma
2016-06-30 22:30   ` Rodrigo Vivi
2016-07-01  6:22     ` Sharma, Shashank
2016-07-02  0:13       ` Rodrigo Vivi
2016-06-21 15:00 ` [PATCH v2 3/4] drm/i915: Parse VBT data for lspcon Shashank Sharma
2016-06-30 22:48   ` Rodrigo Vivi
2016-07-01  6:24     ` Sharma, Shashank
2016-06-21 15:00 ` [PATCH v2 4/4] drm/i915: Enable lspcon initialization Shashank Sharma
2016-06-30 22:53   ` Rodrigo Vivi
2016-07-01  6:27     ` Sharma, Shashank
2016-07-02  0:14       ` Rodrigo Vivi
2016-06-21 15:38 ` ✗ Ro.CI.BAT: failure for Enable lspcon support for GEN9 devices (rev2) Patchwork

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=57760680.6050206@intel.com \
    --to=shashank.sharma@intel.com \
    --cc=dhinakaran.pandiyan@intel.com \
    --cc=intel-gfx@lists.freedesktop.org \
    --cc=paulo.r.zanoni@intel.com \
    --cc=rodrigo.vivi@gmail.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.