[PATCH v2 1/2] drm: Add drm_bridge

2013-08-30 Thread Rob Clark
On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul  wrote:
> This patch adds the notion of a drm_bridge. A bridge is a chained
> device which hangs off an encoder. The drm driver using the bridge
> should provide the association between encoder and bridge. Once a
> bridge is associated with an encoder, it will participate in mode
> set, and dpms (via the enable/disable hooks).
>
> Signed-off-by: Sean Paul 

Ok, I've had a chance to rebase my msm drm-bridge patch on top of this
latest version (which I'll be sending in a couple of minutes)

Reviewed-by: Rob Clark 


> ---
>  drivers/gpu/drm/drm_crtc.c| 50 ++
>  drivers/gpu/drm/drm_crtc_helper.c | 89 
> ++-
>  include/drm/drm_crtc.h| 55 
>  3 files changed, 175 insertions(+), 19 deletions(-)
>
> diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
> index fc83bb9..0311e2b 100644
> --- a/drivers/gpu/drm/drm_crtc.c
> +++ b/drivers/gpu/drm/drm_crtc.c
> @@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
>  }
>  EXPORT_SYMBOL(drm_connector_unplug_all);
>
> +int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
> +   const struct drm_bridge_funcs *funcs)
> +{
> +   int ret;
> +
> +   drm_modeset_lock_all(dev);
> +
> +   ret = drm_mode_object_get(dev, >base, DRM_MODE_OBJECT_BRIDGE);
> +   if (ret)
> +   goto out;
> +
> +   bridge->dev = dev;
> +   bridge->funcs = funcs;
> +
> +   list_add_tail(>head, >mode_config.bridge_list);
> +   dev->mode_config.num_bridge++;
> +
> + out:
> +   drm_modeset_unlock_all(dev);
> +   return ret;
> +}
> +EXPORT_SYMBOL(drm_bridge_init);
> +
> +void drm_bridge_cleanup(struct drm_bridge *bridge)
> +{
> +   struct drm_device *dev = bridge->dev;
> +
> +   drm_modeset_lock_all(dev);
> +   drm_mode_object_put(dev, >base);
> +   list_del(>head);
> +   dev->mode_config.num_bridge--;
> +   drm_modeset_unlock_all(dev);
> +}
> +EXPORT_SYMBOL(drm_bridge_cleanup);
> +
>  int drm_encoder_init(struct drm_device *dev,
>   struct drm_encoder *encoder,
>   const struct drm_encoder_funcs *funcs,
> @@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
> struct drm_mode_group *gr
> total_objects += dev->mode_config.num_crtc;
> total_objects += dev->mode_config.num_connector;
> total_objects += dev->mode_config.num_encoder;
> +   total_objects += dev->mode_config.num_bridge;
>
> group->id_list = kzalloc(total_objects * sizeof(uint32_t), 
> GFP_KERNEL);
> if (!group->id_list)
> @@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
> struct drm_mode_group *gr
> group->num_crtcs = 0;
> group->num_connectors = 0;
> group->num_encoders = 0;
> +   group->num_bridges = 0;
> return 0;
>  }
>
> @@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
> *dev,
> struct drm_crtc *crtc;
> struct drm_encoder *encoder;
> struct drm_connector *connector;
> +   struct drm_bridge *bridge;
> int ret;
>
> if ((ret = drm_mode_group_init(dev, group)))
> @@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct drm_device 
> *dev,
> group->id_list[group->num_crtcs + group->num_encoders +
>group->num_connectors++] = connector->base.id;
>
> +   list_for_each_entry(bridge, >mode_config.bridge_list, head)
> +   group->id_list[group->num_crtcs + group->num_encoders +
> +  group->num_connectors + group->num_bridges++] =
> +   bridge->base.id;
> +
> return 0;
>  }
>  EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
> @@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
> INIT_LIST_HEAD(>mode_config.fb_list);
> INIT_LIST_HEAD(>mode_config.crtc_list);
> INIT_LIST_HEAD(>mode_config.connector_list);
> +   INIT_LIST_HEAD(>mode_config.bridge_list);
> INIT_LIST_HEAD(>mode_config.encoder_list);
> INIT_LIST_HEAD(>mode_config.property_list);
> INIT_LIST_HEAD(>mode_config.property_blob_list);
> @@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
> struct drm_connector *connector, *ot;
> struct drm_crtc *crtc, *ct;
> struct drm_encoder *encoder, *enct;
> +   struct drm_bridge *bridge, *brt;
> struct drm_framebuffer *fb, *fbt;
> struct drm_property *property, *pt;
> struct drm_property_blob *blob, *bt;
> @@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
> encoder->funcs->destroy(encoder);
> }
>
> +   list_for_each_entry_safe(bridge, brt,
> +>mode_config.bridge_list, 

Re: [PATCH v2 1/2] drm: Add drm_bridge

2013-08-30 Thread Rob Clark
On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul seanp...@chromium.org wrote:
 This patch adds the notion of a drm_bridge. A bridge is a chained
 device which hangs off an encoder. The drm driver using the bridge
 should provide the association between encoder and bridge. Once a
 bridge is associated with an encoder, it will participate in mode
 set, and dpms (via the enable/disable hooks).

 Signed-off-by: Sean Paul seanp...@chromium.org

Ok, I've had a chance to rebase my msm drm-bridge patch on top of this
latest version (which I'll be sending in a couple of minutes)

Reviewed-by: Rob Clark robdcl...@gmail.com


 ---
  drivers/gpu/drm/drm_crtc.c| 50 ++
  drivers/gpu/drm/drm_crtc_helper.c | 89 
 ++-
  include/drm/drm_crtc.h| 55 
  3 files changed, 175 insertions(+), 19 deletions(-)

 diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
 index fc83bb9..0311e2b 100644
 --- a/drivers/gpu/drm/drm_crtc.c
 +++ b/drivers/gpu/drm/drm_crtc.c
 @@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
  }
  EXPORT_SYMBOL(drm_connector_unplug_all);

 +int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
 +   const struct drm_bridge_funcs *funcs)
 +{
 +   int ret;
 +
 +   drm_modeset_lock_all(dev);
 +
 +   ret = drm_mode_object_get(dev, bridge-base, DRM_MODE_OBJECT_BRIDGE);
 +   if (ret)
 +   goto out;
 +
 +   bridge-dev = dev;
 +   bridge-funcs = funcs;
 +
 +   list_add_tail(bridge-head, dev-mode_config.bridge_list);
 +   dev-mode_config.num_bridge++;
 +
 + out:
 +   drm_modeset_unlock_all(dev);
 +   return ret;
 +}
 +EXPORT_SYMBOL(drm_bridge_init);
 +
 +void drm_bridge_cleanup(struct drm_bridge *bridge)
 +{
 +   struct drm_device *dev = bridge-dev;
 +
 +   drm_modeset_lock_all(dev);
 +   drm_mode_object_put(dev, bridge-base);
 +   list_del(bridge-head);
 +   dev-mode_config.num_bridge--;
 +   drm_modeset_unlock_all(dev);
 +}
 +EXPORT_SYMBOL(drm_bridge_cleanup);
 +
  int drm_encoder_init(struct drm_device *dev,
   struct drm_encoder *encoder,
   const struct drm_encoder_funcs *funcs,
 @@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
 struct drm_mode_group *gr
 total_objects += dev-mode_config.num_crtc;
 total_objects += dev-mode_config.num_connector;
 total_objects += dev-mode_config.num_encoder;
 +   total_objects += dev-mode_config.num_bridge;

 group-id_list = kzalloc(total_objects * sizeof(uint32_t), 
 GFP_KERNEL);
 if (!group-id_list)
 @@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
 struct drm_mode_group *gr
 group-num_crtcs = 0;
 group-num_connectors = 0;
 group-num_encoders = 0;
 +   group-num_bridges = 0;
 return 0;
  }

 @@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
 *dev,
 struct drm_crtc *crtc;
 struct drm_encoder *encoder;
 struct drm_connector *connector;
 +   struct drm_bridge *bridge;
 int ret;

 if ((ret = drm_mode_group_init(dev, group)))
 @@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct drm_device 
 *dev,
 group-id_list[group-num_crtcs + group-num_encoders +
group-num_connectors++] = connector-base.id;

 +   list_for_each_entry(bridge, dev-mode_config.bridge_list, head)
 +   group-id_list[group-num_crtcs + group-num_encoders +
 +  group-num_connectors + group-num_bridges++] =
 +   bridge-base.id;
 +
 return 0;
  }
  EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
 @@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
 INIT_LIST_HEAD(dev-mode_config.fb_list);
 INIT_LIST_HEAD(dev-mode_config.crtc_list);
 INIT_LIST_HEAD(dev-mode_config.connector_list);
 +   INIT_LIST_HEAD(dev-mode_config.bridge_list);
 INIT_LIST_HEAD(dev-mode_config.encoder_list);
 INIT_LIST_HEAD(dev-mode_config.property_list);
 INIT_LIST_HEAD(dev-mode_config.property_blob_list);
 @@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
 struct drm_connector *connector, *ot;
 struct drm_crtc *crtc, *ct;
 struct drm_encoder *encoder, *enct;
 +   struct drm_bridge *bridge, *brt;
 struct drm_framebuffer *fb, *fbt;
 struct drm_property *property, *pt;
 struct drm_property_blob *blob, *bt;
 @@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
 encoder-funcs-destroy(encoder);
 }

 +   list_for_each_entry_safe(bridge, brt,
 +dev-mode_config.bridge_list, head) {
 +   

[PATCH v2 1/2] drm: Add drm_bridge

2013-08-29 Thread Daniel Vetter
On Thu, Aug 29, 2013 at 12:13:16PM -0400, Rob Clark wrote:
> On Thu, Aug 29, 2013 at 11:59 AM, Sean Paul  wrote:
> > On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul  wrote:
> >> This patch adds the notion of a drm_bridge. A bridge is a chained
> >> device which hangs off an encoder. The drm driver using the bridge
> >> should provide the association between encoder and bridge. Once a
> >> bridge is associated with an encoder, it will participate in mode
> >> set, and dpms (via the enable/disable hooks).
> >>
> >
> > Friendly ping. Any feedback?
> 
> It looks good to me, although unfortunately I've not had a chance to
> rebase on this version.  I'll try to make some time to do that in the
> next few days.

Looks good to me, no more bikesheds from my side. I kinda wanted to port
over some of the stuff we have in drm/i915, but I guess that won't happen
anytime soon. Imo this can go in as soon as we have an in-tree user ready.
-Daniel
-- 
Daniel Vetter
Software Engineer, Intel Corporation
+41 (0) 79 365 57 48 - http://blog.ffwll.ch


[PATCH v2 1/2] drm: Add drm_bridge

2013-08-29 Thread Rob Clark
On Thu, Aug 29, 2013 at 11:59 AM, Sean Paul  wrote:
> On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul  wrote:
>> This patch adds the notion of a drm_bridge. A bridge is a chained
>> device which hangs off an encoder. The drm driver using the bridge
>> should provide the association between encoder and bridge. Once a
>> bridge is associated with an encoder, it will participate in mode
>> set, and dpms (via the enable/disable hooks).
>>
>
> Friendly ping. Any feedback?

It looks good to me, although unfortunately I've not had a chance to
rebase on this version.  I'll try to make some time to do that in the
next few days.

BR,
-R

> Sean
>
>
>> Signed-off-by: Sean Paul 
>> ---
>>  drivers/gpu/drm/drm_crtc.c| 50 ++
>>  drivers/gpu/drm/drm_crtc_helper.c | 89 
>> ++-
>>  include/drm/drm_crtc.h| 55 
>>  3 files changed, 175 insertions(+), 19 deletions(-)
>>
>> diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
>> index fc83bb9..0311e2b 100644
>> --- a/drivers/gpu/drm/drm_crtc.c
>> +++ b/drivers/gpu/drm/drm_crtc.c
>> @@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
>>  }
>>  EXPORT_SYMBOL(drm_connector_unplug_all);
>>
>> +int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
>> +   const struct drm_bridge_funcs *funcs)
>> +{
>> +   int ret;
>> +
>> +   drm_modeset_lock_all(dev);
>> +
>> +   ret = drm_mode_object_get(dev, >base, 
>> DRM_MODE_OBJECT_BRIDGE);
>> +   if (ret)
>> +   goto out;
>> +
>> +   bridge->dev = dev;
>> +   bridge->funcs = funcs;
>> +
>> +   list_add_tail(>head, >mode_config.bridge_list);
>> +   dev->mode_config.num_bridge++;
>> +
>> + out:
>> +   drm_modeset_unlock_all(dev);
>> +   return ret;
>> +}
>> +EXPORT_SYMBOL(drm_bridge_init);
>> +
>> +void drm_bridge_cleanup(struct drm_bridge *bridge)
>> +{
>> +   struct drm_device *dev = bridge->dev;
>> +
>> +   drm_modeset_lock_all(dev);
>> +   drm_mode_object_put(dev, >base);
>> +   list_del(>head);
>> +   dev->mode_config.num_bridge--;
>> +   drm_modeset_unlock_all(dev);
>> +}
>> +EXPORT_SYMBOL(drm_bridge_cleanup);
>> +
>>  int drm_encoder_init(struct drm_device *dev,
>>   struct drm_encoder *encoder,
>>   const struct drm_encoder_funcs *funcs,
>> @@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
>> struct drm_mode_group *gr
>> total_objects += dev->mode_config.num_crtc;
>> total_objects += dev->mode_config.num_connector;
>> total_objects += dev->mode_config.num_encoder;
>> +   total_objects += dev->mode_config.num_bridge;
>>
>> group->id_list = kzalloc(total_objects * sizeof(uint32_t), 
>> GFP_KERNEL);
>> if (!group->id_list)
>> @@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
>> struct drm_mode_group *gr
>> group->num_crtcs = 0;
>> group->num_connectors = 0;
>> group->num_encoders = 0;
>> +   group->num_bridges = 0;
>> return 0;
>>  }
>>
>> @@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
>> *dev,
>> struct drm_crtc *crtc;
>> struct drm_encoder *encoder;
>> struct drm_connector *connector;
>> +   struct drm_bridge *bridge;
>> int ret;
>>
>> if ((ret = drm_mode_group_init(dev, group)))
>> @@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct 
>> drm_device *dev,
>> group->id_list[group->num_crtcs + group->num_encoders +
>>group->num_connectors++] = connector->base.id;
>>
>> +   list_for_each_entry(bridge, >mode_config.bridge_list, head)
>> +   group->id_list[group->num_crtcs + group->num_encoders +
>> +  group->num_connectors + group->num_bridges++] 
>> =
>> +   bridge->base.id;
>> +
>> return 0;
>>  }
>>  EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
>> @@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
>> INIT_LIST_HEAD(>mode_config.fb_list);
>> INIT_LIST_HEAD(>mode_config.crtc_list);
>> INIT_LIST_HEAD(>mode_config.connector_list);
>> +   INIT_LIST_HEAD(>mode_config.bridge_list);
>> INIT_LIST_HEAD(>mode_config.encoder_list);
>> INIT_LIST_HEAD(>mode_config.property_list);
>> INIT_LIST_HEAD(>mode_config.property_blob_list);
>> @@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
>> struct drm_connector *connector, *ot;
>> struct drm_crtc *crtc, *ct;
>> struct drm_encoder *encoder, *enct;
>> +   struct drm_bridge *bridge, *brt;
>> struct drm_framebuffer *fb, *fbt;
>> struct drm_property *property, *pt;
>> struct drm_property_blob *blob, *bt;
>> @@ -3951,6 +3996,11 @@ 

[PATCH v2 1/2] drm: Add drm_bridge

2013-08-29 Thread Sean Paul
On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul  wrote:
> This patch adds the notion of a drm_bridge. A bridge is a chained
> device which hangs off an encoder. The drm driver using the bridge
> should provide the association between encoder and bridge. Once a
> bridge is associated with an encoder, it will participate in mode
> set, and dpms (via the enable/disable hooks).
>

Friendly ping. Any feedback?

Sean


> Signed-off-by: Sean Paul 
> ---
>  drivers/gpu/drm/drm_crtc.c| 50 ++
>  drivers/gpu/drm/drm_crtc_helper.c | 89 
> ++-
>  include/drm/drm_crtc.h| 55 
>  3 files changed, 175 insertions(+), 19 deletions(-)
>
> diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
> index fc83bb9..0311e2b 100644
> --- a/drivers/gpu/drm/drm_crtc.c
> +++ b/drivers/gpu/drm/drm_crtc.c
> @@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
>  }
>  EXPORT_SYMBOL(drm_connector_unplug_all);
>
> +int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
> +   const struct drm_bridge_funcs *funcs)
> +{
> +   int ret;
> +
> +   drm_modeset_lock_all(dev);
> +
> +   ret = drm_mode_object_get(dev, >base, DRM_MODE_OBJECT_BRIDGE);
> +   if (ret)
> +   goto out;
> +
> +   bridge->dev = dev;
> +   bridge->funcs = funcs;
> +
> +   list_add_tail(>head, >mode_config.bridge_list);
> +   dev->mode_config.num_bridge++;
> +
> + out:
> +   drm_modeset_unlock_all(dev);
> +   return ret;
> +}
> +EXPORT_SYMBOL(drm_bridge_init);
> +
> +void drm_bridge_cleanup(struct drm_bridge *bridge)
> +{
> +   struct drm_device *dev = bridge->dev;
> +
> +   drm_modeset_lock_all(dev);
> +   drm_mode_object_put(dev, >base);
> +   list_del(>head);
> +   dev->mode_config.num_bridge--;
> +   drm_modeset_unlock_all(dev);
> +}
> +EXPORT_SYMBOL(drm_bridge_cleanup);
> +
>  int drm_encoder_init(struct drm_device *dev,
>   struct drm_encoder *encoder,
>   const struct drm_encoder_funcs *funcs,
> @@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
> struct drm_mode_group *gr
> total_objects += dev->mode_config.num_crtc;
> total_objects += dev->mode_config.num_connector;
> total_objects += dev->mode_config.num_encoder;
> +   total_objects += dev->mode_config.num_bridge;
>
> group->id_list = kzalloc(total_objects * sizeof(uint32_t), 
> GFP_KERNEL);
> if (!group->id_list)
> @@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
> struct drm_mode_group *gr
> group->num_crtcs = 0;
> group->num_connectors = 0;
> group->num_encoders = 0;
> +   group->num_bridges = 0;
> return 0;
>  }
>
> @@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
> *dev,
> struct drm_crtc *crtc;
> struct drm_encoder *encoder;
> struct drm_connector *connector;
> +   struct drm_bridge *bridge;
> int ret;
>
> if ((ret = drm_mode_group_init(dev, group)))
> @@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct drm_device 
> *dev,
> group->id_list[group->num_crtcs + group->num_encoders +
>group->num_connectors++] = connector->base.id;
>
> +   list_for_each_entry(bridge, >mode_config.bridge_list, head)
> +   group->id_list[group->num_crtcs + group->num_encoders +
> +  group->num_connectors + group->num_bridges++] =
> +   bridge->base.id;
> +
> return 0;
>  }
>  EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
> @@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
> INIT_LIST_HEAD(>mode_config.fb_list);
> INIT_LIST_HEAD(>mode_config.crtc_list);
> INIT_LIST_HEAD(>mode_config.connector_list);
> +   INIT_LIST_HEAD(>mode_config.bridge_list);
> INIT_LIST_HEAD(>mode_config.encoder_list);
> INIT_LIST_HEAD(>mode_config.property_list);
> INIT_LIST_HEAD(>mode_config.property_blob_list);
> @@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
> struct drm_connector *connector, *ot;
> struct drm_crtc *crtc, *ct;
> struct drm_encoder *encoder, *enct;
> +   struct drm_bridge *bridge, *brt;
> struct drm_framebuffer *fb, *fbt;
> struct drm_property *property, *pt;
> struct drm_property_blob *blob, *bt;
> @@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
> encoder->funcs->destroy(encoder);
> }
>
> +   list_for_each_entry_safe(bridge, brt,
> +>mode_config.bridge_list, head) {
> +   bridge->funcs->destroy(bridge);
> +   }
> +
> list_for_each_entry_safe(connector, ot,

Re: [PATCH v2 1/2] drm: Add drm_bridge

2013-08-29 Thread Sean Paul
On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul seanp...@chromium.org wrote:
 This patch adds the notion of a drm_bridge. A bridge is a chained
 device which hangs off an encoder. The drm driver using the bridge
 should provide the association between encoder and bridge. Once a
 bridge is associated with an encoder, it will participate in mode
 set, and dpms (via the enable/disable hooks).


Friendly ping. Any feedback?

Sean


 Signed-off-by: Sean Paul seanp...@chromium.org
 ---
  drivers/gpu/drm/drm_crtc.c| 50 ++
  drivers/gpu/drm/drm_crtc_helper.c | 89 
 ++-
  include/drm/drm_crtc.h| 55 
  3 files changed, 175 insertions(+), 19 deletions(-)

 diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
 index fc83bb9..0311e2b 100644
 --- a/drivers/gpu/drm/drm_crtc.c
 +++ b/drivers/gpu/drm/drm_crtc.c
 @@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
  }
  EXPORT_SYMBOL(drm_connector_unplug_all);

 +int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
 +   const struct drm_bridge_funcs *funcs)
 +{
 +   int ret;
 +
 +   drm_modeset_lock_all(dev);
 +
 +   ret = drm_mode_object_get(dev, bridge-base, DRM_MODE_OBJECT_BRIDGE);
 +   if (ret)
 +   goto out;
 +
 +   bridge-dev = dev;
 +   bridge-funcs = funcs;
 +
 +   list_add_tail(bridge-head, dev-mode_config.bridge_list);
 +   dev-mode_config.num_bridge++;
 +
 + out:
 +   drm_modeset_unlock_all(dev);
 +   return ret;
 +}
 +EXPORT_SYMBOL(drm_bridge_init);
 +
 +void drm_bridge_cleanup(struct drm_bridge *bridge)
 +{
 +   struct drm_device *dev = bridge-dev;
 +
 +   drm_modeset_lock_all(dev);
 +   drm_mode_object_put(dev, bridge-base);
 +   list_del(bridge-head);
 +   dev-mode_config.num_bridge--;
 +   drm_modeset_unlock_all(dev);
 +}
 +EXPORT_SYMBOL(drm_bridge_cleanup);
 +
  int drm_encoder_init(struct drm_device *dev,
   struct drm_encoder *encoder,
   const struct drm_encoder_funcs *funcs,
 @@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
 struct drm_mode_group *gr
 total_objects += dev-mode_config.num_crtc;
 total_objects += dev-mode_config.num_connector;
 total_objects += dev-mode_config.num_encoder;
 +   total_objects += dev-mode_config.num_bridge;

 group-id_list = kzalloc(total_objects * sizeof(uint32_t), 
 GFP_KERNEL);
 if (!group-id_list)
 @@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
 struct drm_mode_group *gr
 group-num_crtcs = 0;
 group-num_connectors = 0;
 group-num_encoders = 0;
 +   group-num_bridges = 0;
 return 0;
  }

 @@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
 *dev,
 struct drm_crtc *crtc;
 struct drm_encoder *encoder;
 struct drm_connector *connector;
 +   struct drm_bridge *bridge;
 int ret;

 if ((ret = drm_mode_group_init(dev, group)))
 @@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct drm_device 
 *dev,
 group-id_list[group-num_crtcs + group-num_encoders +
group-num_connectors++] = connector-base.id;

 +   list_for_each_entry(bridge, dev-mode_config.bridge_list, head)
 +   group-id_list[group-num_crtcs + group-num_encoders +
 +  group-num_connectors + group-num_bridges++] =
 +   bridge-base.id;
 +
 return 0;
  }
  EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
 @@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
 INIT_LIST_HEAD(dev-mode_config.fb_list);
 INIT_LIST_HEAD(dev-mode_config.crtc_list);
 INIT_LIST_HEAD(dev-mode_config.connector_list);
 +   INIT_LIST_HEAD(dev-mode_config.bridge_list);
 INIT_LIST_HEAD(dev-mode_config.encoder_list);
 INIT_LIST_HEAD(dev-mode_config.property_list);
 INIT_LIST_HEAD(dev-mode_config.property_blob_list);
 @@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
 struct drm_connector *connector, *ot;
 struct drm_crtc *crtc, *ct;
 struct drm_encoder *encoder, *enct;
 +   struct drm_bridge *bridge, *brt;
 struct drm_framebuffer *fb, *fbt;
 struct drm_property *property, *pt;
 struct drm_property_blob *blob, *bt;
 @@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
 encoder-funcs-destroy(encoder);
 }

 +   list_for_each_entry_safe(bridge, brt,
 +dev-mode_config.bridge_list, head) {
 +   bridge-funcs-destroy(bridge);
 +   }
 +
 list_for_each_entry_safe(connector, ot,
  

Re: [PATCH v2 1/2] drm: Add drm_bridge

2013-08-29 Thread Rob Clark
On Thu, Aug 29, 2013 at 11:59 AM, Sean Paul seanp...@chromium.org wrote:
 On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul seanp...@chromium.org wrote:
 This patch adds the notion of a drm_bridge. A bridge is a chained
 device which hangs off an encoder. The drm driver using the bridge
 should provide the association between encoder and bridge. Once a
 bridge is associated with an encoder, it will participate in mode
 set, and dpms (via the enable/disable hooks).


 Friendly ping. Any feedback?

It looks good to me, although unfortunately I've not had a chance to
rebase on this version.  I'll try to make some time to do that in the
next few days.

BR,
-R

 Sean


 Signed-off-by: Sean Paul seanp...@chromium.org
 ---
  drivers/gpu/drm/drm_crtc.c| 50 ++
  drivers/gpu/drm/drm_crtc_helper.c | 89 
 ++-
  include/drm/drm_crtc.h| 55 
  3 files changed, 175 insertions(+), 19 deletions(-)

 diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
 index fc83bb9..0311e2b 100644
 --- a/drivers/gpu/drm/drm_crtc.c
 +++ b/drivers/gpu/drm/drm_crtc.c
 @@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
  }
  EXPORT_SYMBOL(drm_connector_unplug_all);

 +int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
 +   const struct drm_bridge_funcs *funcs)
 +{
 +   int ret;
 +
 +   drm_modeset_lock_all(dev);
 +
 +   ret = drm_mode_object_get(dev, bridge-base, 
 DRM_MODE_OBJECT_BRIDGE);
 +   if (ret)
 +   goto out;
 +
 +   bridge-dev = dev;
 +   bridge-funcs = funcs;
 +
 +   list_add_tail(bridge-head, dev-mode_config.bridge_list);
 +   dev-mode_config.num_bridge++;
 +
 + out:
 +   drm_modeset_unlock_all(dev);
 +   return ret;
 +}
 +EXPORT_SYMBOL(drm_bridge_init);
 +
 +void drm_bridge_cleanup(struct drm_bridge *bridge)
 +{
 +   struct drm_device *dev = bridge-dev;
 +
 +   drm_modeset_lock_all(dev);
 +   drm_mode_object_put(dev, bridge-base);
 +   list_del(bridge-head);
 +   dev-mode_config.num_bridge--;
 +   drm_modeset_unlock_all(dev);
 +}
 +EXPORT_SYMBOL(drm_bridge_cleanup);
 +
  int drm_encoder_init(struct drm_device *dev,
   struct drm_encoder *encoder,
   const struct drm_encoder_funcs *funcs,
 @@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
 struct drm_mode_group *gr
 total_objects += dev-mode_config.num_crtc;
 total_objects += dev-mode_config.num_connector;
 total_objects += dev-mode_config.num_encoder;
 +   total_objects += dev-mode_config.num_bridge;

 group-id_list = kzalloc(total_objects * sizeof(uint32_t), 
 GFP_KERNEL);
 if (!group-id_list)
 @@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
 struct drm_mode_group *gr
 group-num_crtcs = 0;
 group-num_connectors = 0;
 group-num_encoders = 0;
 +   group-num_bridges = 0;
 return 0;
  }

 @@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
 *dev,
 struct drm_crtc *crtc;
 struct drm_encoder *encoder;
 struct drm_connector *connector;
 +   struct drm_bridge *bridge;
 int ret;

 if ((ret = drm_mode_group_init(dev, group)))
 @@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct 
 drm_device *dev,
 group-id_list[group-num_crtcs + group-num_encoders +
group-num_connectors++] = connector-base.id;

 +   list_for_each_entry(bridge, dev-mode_config.bridge_list, head)
 +   group-id_list[group-num_crtcs + group-num_encoders +
 +  group-num_connectors + group-num_bridges++] 
 =
 +   bridge-base.id;
 +
 return 0;
  }
  EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
 @@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
 INIT_LIST_HEAD(dev-mode_config.fb_list);
 INIT_LIST_HEAD(dev-mode_config.crtc_list);
 INIT_LIST_HEAD(dev-mode_config.connector_list);
 +   INIT_LIST_HEAD(dev-mode_config.bridge_list);
 INIT_LIST_HEAD(dev-mode_config.encoder_list);
 INIT_LIST_HEAD(dev-mode_config.property_list);
 INIT_LIST_HEAD(dev-mode_config.property_blob_list);
 @@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
 struct drm_connector *connector, *ot;
 struct drm_crtc *crtc, *ct;
 struct drm_encoder *encoder, *enct;
 +   struct drm_bridge *bridge, *brt;
 struct drm_framebuffer *fb, *fbt;
 struct drm_property *property, *pt;
 struct drm_property_blob *blob, *bt;
 @@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
 encoder-funcs-destroy(encoder);
 }

 +   list_for_each_entry_safe(bridge, brt,

Re: [PATCH v2 1/2] drm: Add drm_bridge

2013-08-29 Thread Daniel Vetter
On Thu, Aug 29, 2013 at 12:13:16PM -0400, Rob Clark wrote:
 On Thu, Aug 29, 2013 at 11:59 AM, Sean Paul seanp...@chromium.org wrote:
  On Wed, Aug 14, 2013 at 4:47 PM, Sean Paul seanp...@chromium.org wrote:
  This patch adds the notion of a drm_bridge. A bridge is a chained
  device which hangs off an encoder. The drm driver using the bridge
  should provide the association between encoder and bridge. Once a
  bridge is associated with an encoder, it will participate in mode
  set, and dpms (via the enable/disable hooks).
 
 
  Friendly ping. Any feedback?
 
 It looks good to me, although unfortunately I've not had a chance to
 rebase on this version.  I'll try to make some time to do that in the
 next few days.

Looks good to me, no more bikesheds from my side. I kinda wanted to port
over some of the stuff we have in drm/i915, but I guess that won't happen
anytime soon. Imo this can go in as soon as we have an in-tree user ready.
-Daniel
-- 
Daniel Vetter
Software Engineer, Intel Corporation
+41 (0) 79 365 57 48 - http://blog.ffwll.ch
___
dri-devel mailing list
dri-devel@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/dri-devel


[PATCH v2 1/2] drm: Add drm_bridge

2013-08-14 Thread Sean Paul
This patch adds the notion of a drm_bridge. A bridge is a chained
device which hangs off an encoder. The drm driver using the bridge
should provide the association between encoder and bridge. Once a
bridge is associated with an encoder, it will participate in mode
set, and dpms (via the enable/disable hooks).

Signed-off-by: Sean Paul 
---
 drivers/gpu/drm/drm_crtc.c| 50 ++
 drivers/gpu/drm/drm_crtc_helper.c | 89 ++-
 include/drm/drm_crtc.h| 55 
 3 files changed, 175 insertions(+), 19 deletions(-)

diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
index fc83bb9..0311e2b 100644
--- a/drivers/gpu/drm/drm_crtc.c
+++ b/drivers/gpu/drm/drm_crtc.c
@@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
 }
 EXPORT_SYMBOL(drm_connector_unplug_all);

+int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
+   const struct drm_bridge_funcs *funcs)
+{
+   int ret;
+
+   drm_modeset_lock_all(dev);
+
+   ret = drm_mode_object_get(dev, >base, DRM_MODE_OBJECT_BRIDGE);
+   if (ret)
+   goto out;
+
+   bridge->dev = dev;
+   bridge->funcs = funcs;
+
+   list_add_tail(>head, >mode_config.bridge_list);
+   dev->mode_config.num_bridge++;
+
+ out:
+   drm_modeset_unlock_all(dev);
+   return ret;
+}
+EXPORT_SYMBOL(drm_bridge_init);
+
+void drm_bridge_cleanup(struct drm_bridge *bridge)
+{
+   struct drm_device *dev = bridge->dev;
+
+   drm_modeset_lock_all(dev);
+   drm_mode_object_put(dev, >base);
+   list_del(>head);
+   dev->mode_config.num_bridge--;
+   drm_modeset_unlock_all(dev);
+}
+EXPORT_SYMBOL(drm_bridge_cleanup);
+
 int drm_encoder_init(struct drm_device *dev,
  struct drm_encoder *encoder,
  const struct drm_encoder_funcs *funcs,
@@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
struct drm_mode_group *gr
total_objects += dev->mode_config.num_crtc;
total_objects += dev->mode_config.num_connector;
total_objects += dev->mode_config.num_encoder;
+   total_objects += dev->mode_config.num_bridge;

group->id_list = kzalloc(total_objects * sizeof(uint32_t), GFP_KERNEL);
if (!group->id_list)
@@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
struct drm_mode_group *gr
group->num_crtcs = 0;
group->num_connectors = 0;
group->num_encoders = 0;
+   group->num_bridges = 0;
return 0;
 }

@@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
*dev,
struct drm_crtc *crtc;
struct drm_encoder *encoder;
struct drm_connector *connector;
+   struct drm_bridge *bridge;
int ret;

if ((ret = drm_mode_group_init(dev, group)))
@@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct drm_device 
*dev,
group->id_list[group->num_crtcs + group->num_encoders +
   group->num_connectors++] = connector->base.id;

+   list_for_each_entry(bridge, >mode_config.bridge_list, head)
+   group->id_list[group->num_crtcs + group->num_encoders +
+  group->num_connectors + group->num_bridges++] =
+   bridge->base.id;
+
return 0;
 }
 EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
@@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
INIT_LIST_HEAD(>mode_config.fb_list);
INIT_LIST_HEAD(>mode_config.crtc_list);
INIT_LIST_HEAD(>mode_config.connector_list);
+   INIT_LIST_HEAD(>mode_config.bridge_list);
INIT_LIST_HEAD(>mode_config.encoder_list);
INIT_LIST_HEAD(>mode_config.property_list);
INIT_LIST_HEAD(>mode_config.property_blob_list);
@@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
struct drm_connector *connector, *ot;
struct drm_crtc *crtc, *ct;
struct drm_encoder *encoder, *enct;
+   struct drm_bridge *bridge, *brt;
struct drm_framebuffer *fb, *fbt;
struct drm_property *property, *pt;
struct drm_property_blob *blob, *bt;
@@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
encoder->funcs->destroy(encoder);
}

+   list_for_each_entry_safe(bridge, brt,
+>mode_config.bridge_list, head) {
+   bridge->funcs->destroy(bridge);
+   }
+
list_for_each_entry_safe(connector, ot,
 >mode_config.connector_list, head) {
connector->funcs->destroy(connector);
diff --git a/drivers/gpu/drm/drm_crtc_helper.c 
b/drivers/gpu/drm/drm_crtc_helper.c
index 6a64749..c722c3b 100644
--- a/drivers/gpu/drm/drm_crtc_helper.c
+++ b/drivers/gpu/drm/drm_crtc_helper.c
@@ -257,10 +257,16 

[PATCH v2 1/2] drm: Add drm_bridge

2013-08-14 Thread Sean Paul
This patch adds the notion of a drm_bridge. A bridge is a chained
device which hangs off an encoder. The drm driver using the bridge
should provide the association between encoder and bridge. Once a
bridge is associated with an encoder, it will participate in mode
set, and dpms (via the enable/disable hooks).

Signed-off-by: Sean Paul seanp...@chromium.org
---
 drivers/gpu/drm/drm_crtc.c| 50 ++
 drivers/gpu/drm/drm_crtc_helper.c | 89 ++-
 include/drm/drm_crtc.h| 55 
 3 files changed, 175 insertions(+), 19 deletions(-)

diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
index fc83bb9..0311e2b 100644
--- a/drivers/gpu/drm/drm_crtc.c
+++ b/drivers/gpu/drm/drm_crtc.c
@@ -781,6 +781,41 @@ void drm_connector_unplug_all(struct drm_device *dev)
 }
 EXPORT_SYMBOL(drm_connector_unplug_all);
 
+int drm_bridge_init(struct drm_device *dev, struct drm_bridge *bridge,
+   const struct drm_bridge_funcs *funcs)
+{
+   int ret;
+
+   drm_modeset_lock_all(dev);
+
+   ret = drm_mode_object_get(dev, bridge-base, DRM_MODE_OBJECT_BRIDGE);
+   if (ret)
+   goto out;
+
+   bridge-dev = dev;
+   bridge-funcs = funcs;
+
+   list_add_tail(bridge-head, dev-mode_config.bridge_list);
+   dev-mode_config.num_bridge++;
+
+ out:
+   drm_modeset_unlock_all(dev);
+   return ret;
+}
+EXPORT_SYMBOL(drm_bridge_init);
+
+void drm_bridge_cleanup(struct drm_bridge *bridge)
+{
+   struct drm_device *dev = bridge-dev;
+
+   drm_modeset_lock_all(dev);
+   drm_mode_object_put(dev, bridge-base);
+   list_del(bridge-head);
+   dev-mode_config.num_bridge--;
+   drm_modeset_unlock_all(dev);
+}
+EXPORT_SYMBOL(drm_bridge_cleanup);
+
 int drm_encoder_init(struct drm_device *dev,
  struct drm_encoder *encoder,
  const struct drm_encoder_funcs *funcs,
@@ -1190,6 +1225,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
struct drm_mode_group *gr
total_objects += dev-mode_config.num_crtc;
total_objects += dev-mode_config.num_connector;
total_objects += dev-mode_config.num_encoder;
+   total_objects += dev-mode_config.num_bridge;
 
group-id_list = kzalloc(total_objects * sizeof(uint32_t), GFP_KERNEL);
if (!group-id_list)
@@ -1198,6 +1234,7 @@ static int drm_mode_group_init(struct drm_device *dev, 
struct drm_mode_group *gr
group-num_crtcs = 0;
group-num_connectors = 0;
group-num_encoders = 0;
+   group-num_bridges = 0;
return 0;
 }
 
@@ -1207,6 +1244,7 @@ int drm_mode_group_init_legacy_group(struct drm_device 
*dev,
struct drm_crtc *crtc;
struct drm_encoder *encoder;
struct drm_connector *connector;
+   struct drm_bridge *bridge;
int ret;
 
if ((ret = drm_mode_group_init(dev, group)))
@@ -1223,6 +1261,11 @@ int drm_mode_group_init_legacy_group(struct drm_device 
*dev,
group-id_list[group-num_crtcs + group-num_encoders +
   group-num_connectors++] = connector-base.id;
 
+   list_for_each_entry(bridge, dev-mode_config.bridge_list, head)
+   group-id_list[group-num_crtcs + group-num_encoders +
+  group-num_connectors + group-num_bridges++] =
+   bridge-base.id;
+
return 0;
 }
 EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
@@ -3905,6 +3948,7 @@ void drm_mode_config_init(struct drm_device *dev)
INIT_LIST_HEAD(dev-mode_config.fb_list);
INIT_LIST_HEAD(dev-mode_config.crtc_list);
INIT_LIST_HEAD(dev-mode_config.connector_list);
+   INIT_LIST_HEAD(dev-mode_config.bridge_list);
INIT_LIST_HEAD(dev-mode_config.encoder_list);
INIT_LIST_HEAD(dev-mode_config.property_list);
INIT_LIST_HEAD(dev-mode_config.property_blob_list);
@@ -3941,6 +3985,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
struct drm_connector *connector, *ot;
struct drm_crtc *crtc, *ct;
struct drm_encoder *encoder, *enct;
+   struct drm_bridge *bridge, *brt;
struct drm_framebuffer *fb, *fbt;
struct drm_property *property, *pt;
struct drm_property_blob *blob, *bt;
@@ -3951,6 +3996,11 @@ void drm_mode_config_cleanup(struct drm_device *dev)
encoder-funcs-destroy(encoder);
}
 
+   list_for_each_entry_safe(bridge, brt,
+dev-mode_config.bridge_list, head) {
+   bridge-funcs-destroy(bridge);
+   }
+
list_for_each_entry_safe(connector, ot,
 dev-mode_config.connector_list, head) {
connector-funcs-destroy(connector);
diff --git a/drivers/gpu/drm/drm_crtc_helper.c 
b/drivers/gpu/drm/drm_crtc_helper.c
index 6a64749..c722c3b 100644
--- a/drivers/gpu/drm/drm_crtc_helper.c
+++