[RFC,2/2] drm_hwcomposer: Fall back to client compositon if the gl precompostior fails

Message ID 1524528404-12331-2-git-send-email-john.stultz@linaro.org
State New
Headers show
Series
  • [RFC,1/2] drm_hwcomposer: Cleanup gl precompositor init and provide uses_GL flag
Related show

Commit Message

John Stultz April 24, 2018, 12:06 a.m.
If the gl precompositor isn't being used, we cannot accept
every layer as a device composited layer.

Thus this patch adds some extra logic in the validate function
to try to map layers to available device planes, falling back
to client side compositing if we run-out of planes.

Credit to Rob Herring, who's work this single plane patch was
originally based on.

Feedback or alternative ideas would be greatly appreciated!

Cc: Marissa Wall <marissaw@google.com>
Cc: Sean Paul <seanpaul@google.com>
Cc: Dmitry Shmidt <dimitrysh@google.com>
Cc: Robert Foss <robert.foss@collabora.com>
Cc: Matt Szczesiak <matt.szczesiak@arm.com>
Cc: Liviu Dudau <Liviu.Dudau@arm.com>
Cc: David Hanna <david.hanna11@gmail.com>
Cc: Rob Herring <rob.herring@linaro.org>
Cc: Alexandru-Cosmin Gheorghe <Alexandru-Cosmin.Gheorghe@arm.com>
Cc: Alistair Strachan <astrachan@google.com>
Signed-off-by: John Stultz <john.stultz@linaro.org>

Signed-off-by: John Stultz <john.stultz@linaro.org>

---
 drmhwctwo.cpp | 18 ++++++++++++++++++
 1 file changed, 18 insertions(+)

-- 
2.7.4

Comments

John Stultz April 24, 2018, 12:09 a.m. | #1
On Mon, Apr 23, 2018 at 5:06 PM, John Stultz <john.stultz@linaro.org> wrote:
> If the gl precompositor isn't being used, we cannot accept
> every layer as a device composited layer.
>
> Thus this patch adds some extra logic in the validate function
> to try to map layers to available device planes, falling back
> to client side compositing if we run-out of planes.
>
> Credit to Rob Herring, who's work this single plane patch was
> originally based on.
>
> Feedback or alternative ideas would be greatly appreciated!
>
> Cc: Marissa Wall <marissaw@google.com>
> Cc: Sean Paul <seanpaul@google.com>
> Cc: Dmitry Shmidt <dimitrysh@google.com>
> Cc: Robert Foss <robert.foss@collabora.com>
> Cc: Matt Szczesiak <matt.szczesiak@arm.com>
> Cc: Liviu Dudau <Liviu.Dudau@arm.com>
> Cc: David Hanna <david.hanna11@gmail.com>
> Cc: Rob Herring <rob.herring@linaro.org>
> Cc: Alexandru-Cosmin Gheorghe <Alexandru-Cosmin.Gheorghe@arm.com>
> Cc: Alistair Strachan <astrachan@google.com>
> Signed-off-by: John Stultz <john.stultz@linaro.org>
> Signed-off-by: John Stultz <john.stultz@linaro.org>

A patch so nice, I signed it off twice! :P

Sorry, looks like I yanked and pasted one too many lines from the cc list.

-john
Alexandru-Cosmin Gheorghe April 24, 2018, 8:09 a.m. | #2
On Mon, Apr 23, 2018 at 05:06:44PM -0700, John Stultz wrote:
> If the gl precompositor isn't being used, we cannot accept
> every layer as a device composited layer.
> 
> Thus this patch adds some extra logic in the validate function
> to try to map layers to available device planes, falling back
> to client side compositing if we run-out of planes.
> 
> Credit to Rob Herring, who's work this single plane patch was
> originally based on.
> 
> Feedback or alternative ideas would be greatly appreciated!
> 
> Cc: Marissa Wall <marissaw@google.com>
> Cc: Sean Paul <seanpaul@google.com>
> Cc: Dmitry Shmidt <dimitrysh@google.com>
> Cc: Robert Foss <robert.foss@collabora.com>
> Cc: Matt Szczesiak <matt.szczesiak@arm.com>
> Cc: Liviu Dudau <Liviu.Dudau@arm.com>
> Cc: David Hanna <david.hanna11@gmail.com>
> Cc: Rob Herring <rob.herring@linaro.org>
> Cc: Alexandru-Cosmin Gheorghe <Alexandru-Cosmin.Gheorghe@arm.com>
> Cc: Alistair Strachan <astrachan@google.com>
> Signed-off-by: John Stultz <john.stultz@linaro.org>
> Signed-off-by: John Stultz <john.stultz@linaro.org>
> ---
>  drmhwctwo.cpp | 18 ++++++++++++++++++
>  1 file changed, 18 insertions(+)
> 
> diff --git a/drmhwctwo.cpp b/drmhwctwo.cpp
> index dfca1a6..437a439 100644
> --- a/drmhwctwo.cpp
> +++ b/drmhwctwo.cpp
> @@ -686,6 +686,15 @@ HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
>    supported(__func__);
>    *num_types = 0;
>    *num_requests = 0;
> +  int avail_planes = primary_planes_.size() + overlay_planes_.size();
> +
> +  /*
> +   * If more layers then planes, save one plane
> +   * for client composited layers
> +   */
> +  if (avail_planes < layers_.size())
> +	avail_planes--;
> +
>    for (std::pair<const hwc2_layer_t, DrmHwcTwo::HwcLayer> &l : layers_) {
>      DrmHwcTwo::HwcLayer &layer = l.second;
>      switch (layer.sf_type()) {
> @@ -695,6 +704,15 @@ HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
>          layer.set_validated_type(HWC2::Composition::Client);
>          ++*num_types;
>          break;
> +      case HWC2::Composition::Device:
> +        if (!compositor_.uses_GL() && !avail_planes) {

Something is not entirely correct here, you can't assume just because
you have planes available they can be used. 
E.g Layer has rotation, but the plane doesn't support it.
This part is handled by the planning part in presentDisplay which
falls back on GPU.

I think the easiest and safe way is to just fallback to
Composition::Client whenever the GLCompositor failed to initialize.


> +          layer.set_validated_type(HWC2::Composition::Client);
> +          ++*num_types;
> +          break;
> +        } else {
> +	   avail_planes--;
> +	}
> +	/* fall through */
>        default:
>          layer.set_validated_type(layer.sf_type());
>          break;
> -- 
> 2.7.4
Stefan Schake April 24, 2018, 10:34 a.m. | #3
On Tue, Apr 24, 2018 at 10:09 AM, Alexandru-Cosmin Gheorghe
<Alexandru-Cosmin.Gheorghe@arm.com> wrote:
> On Mon, Apr 23, 2018 at 05:06:44PM -0700, John Stultz wrote:
>> If the gl precompositor isn't being used, we cannot accept
>> every layer as a device composited layer.
>>
>> Thus this patch adds some extra logic in the validate function
>> to try to map layers to available device planes, falling back
>> to client side compositing if we run-out of planes.
>>
>> Credit to Rob Herring, who's work this single plane patch was
>> originally based on.
>>
>> Feedback or alternative ideas would be greatly appreciated!
>>
>> Cc: Marissa Wall <marissaw@google.com>
>> Cc: Sean Paul <seanpaul@google.com>
>> Cc: Dmitry Shmidt <dimitrysh@google.com>
>> Cc: Robert Foss <robert.foss@collabora.com>
>> Cc: Matt Szczesiak <matt.szczesiak@arm.com>
>> Cc: Liviu Dudau <Liviu.Dudau@arm.com>
>> Cc: David Hanna <david.hanna11@gmail.com>
>> Cc: Rob Herring <rob.herring@linaro.org>
>> Cc: Alexandru-Cosmin Gheorghe <Alexandru-Cosmin.Gheorghe@arm.com>
>> Cc: Alistair Strachan <astrachan@google.com>
>> Signed-off-by: John Stultz <john.stultz@linaro.org>
>> Signed-off-by: John Stultz <john.stultz@linaro.org>
>> ---
>>  drmhwctwo.cpp | 18 ++++++++++++++++++
>>  1 file changed, 18 insertions(+)
>>
>> diff --git a/drmhwctwo.cpp b/drmhwctwo.cpp
>> index dfca1a6..437a439 100644
>> --- a/drmhwctwo.cpp
>> +++ b/drmhwctwo.cpp
>> @@ -686,6 +686,15 @@ HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
>>    supported(__func__);
>>    *num_types = 0;
>>    *num_requests = 0;
>> +  int avail_planes = primary_planes_.size() + overlay_planes_.size();
>> +
>> +  /*
>> +   * If more layers then planes, save one plane
>> +   * for client composited layers
>> +   */
>> +  if (avail_planes < layers_.size())
>> +     avail_planes--;
>> +
>>    for (std::pair<const hwc2_layer_t, DrmHwcTwo::HwcLayer> &l : layers_) {
>>      DrmHwcTwo::HwcLayer &layer = l.second;
>>      switch (layer.sf_type()) {
>> @@ -695,6 +704,15 @@ HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
>>          layer.set_validated_type(HWC2::Composition::Client);
>>          ++*num_types;
>>          break;
>> +      case HWC2::Composition::Device:
>> +        if (!compositor_.uses_GL() && !avail_planes) {
>
> Something is not entirely correct here, you can't assume just because
> you have planes available they can be used.
> E.g Layer has rotation, but the plane doesn't support it.
> This part is handled by the planning part in presentDisplay which
> falls back on GPU.
>
> I think the easiest and safe way is to just fallback to
> Composition::Client whenever the GLCompositor failed to initialize.
>

I agree, this would only work out for the single plane case where you end
up using client composition for everything.

In the spirit of DRM what we would probably want is to atomic test a
composition, and if that fails we can still fallback to client or GL
compositor depending on its availability. And then in a far far away
future we might even do a few iterations simplifying our composition until
it atomic tests correctly so we can still offload some "simple" parts
like the cursor.

Thanks,
Stefan
John Stultz April 24, 2018, 6:38 p.m. | #4
On Tue, Apr 24, 2018 at 3:34 AM, Stefan Schake <stschake@gmail.com> wrote:
> On Tue, Apr 24, 2018 at 10:09 AM, Alexandru-Cosmin Gheorghe
> <Alexandru-Cosmin.Gheorghe@arm.com> wrote:
>> On Mon, Apr 23, 2018 at 05:06:44PM -0700, John Stultz wrote:
>>> @@ -695,6 +704,15 @@ HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
>>>          layer.set_validated_type(HWC2::Composition::Client);
>>>          ++*num_types;
>>>          break;
>>> +      case HWC2::Composition::Device:
>>> +        if (!compositor_.uses_GL() && !avail_planes) {
>>
>> Something is not entirely correct here, you can't assume just because
>> you have planes available they can be used.
>> E.g Layer has rotation, but the plane doesn't support it.
>> This part is handled by the planning part in presentDisplay which
>> falls back on GPU.

Ah. Thanks for the correction here!

This is part of the disconnect I have been having with the
drm_hwcomposer logic. The plan/validate step doesn't really do either,
instead it defers all the checking/planning to the set/present step.
But unfortunately it seems if we want to use the surfaceflinger gl
composer, we need to mark the layers as client rendered in the
validate function.

>> I think the easiest and safe way is to just fallback to
>> Composition::Client whenever the GLCompositor failed to initialize.
>>
>
> I agree, this would only work out for the single plane case where you end
> up using client composition for everything.

True, but maybe as a first step we simply fall back on the
glcompositor, just so we have something displaying in that case (right
now nothing gets displayed).

> In the spirit of DRM what we would probably want is to atomic test a
> composition, and if that fails we can still fallback to client or GL
> compositor depending on its availability. And then in a far far away
> future we might even do a few iterations simplifying our composition until
> it atomic tests correctly so we can still offload some "simple" parts
> like the cursor.

This sounds reasonable. I suspect it will take some heavier rework of
the drm_hwcomposer to move such logic to the validate step.

Marissa/Sean: Any objections here? Doing more planning in the validate
step sounds like it aligns closer to the HWC2 interface goals, but I
don't want to have to relearn-the-hard-way any lessons that resulted
in the current mode of accept it all and sort it in present.

In the meantime I'll drop the flawed plane/layer allocation from this
patch and resend.

thanks
-john
Sean Paul April 24, 2018, 7:40 p.m. | #5
On Tue, Apr 24, 2018 at 2:38 PM John Stultz <john.stultz@linaro.org> wrote:

> On Tue, Apr 24, 2018 at 3:34 AM, Stefan Schake <stschake@gmail.com> wrote:
> > On Tue, Apr 24, 2018 at 10:09 AM, Alexandru-Cosmin Gheorghe
> > <Alexandru-Cosmin.Gheorghe@arm.com> wrote:
> >> On Mon, Apr 23, 2018 at 05:06:44PM -0700, John Stultz wrote:
> >>> @@ -695,6 +704,15 @@ HWC2::Error
DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
> >>>          layer.set_validated_type(HWC2::Composition::Client);
> >>>          ++*num_types;
> >>>          break;
> >>> +      case HWC2::Composition::Device:
> >>> +        if (!compositor_.uses_GL() && !avail_planes) {
> >>
> >> Something is not entirely correct here, you can't assume just because
> >> you have planes available they can be used.
> >> E.g Layer has rotation, but the plane doesn't support it.
> >> This part is handled by the planning part in presentDisplay which
> >> falls back on GPU.

> Ah. Thanks for the correction here!

> This is part of the disconnect I have been having with the
> drm_hwcomposer logic. The plan/validate step doesn't really do either,
> instead it defers all the checking/planning to the set/present step.
> But unfortunately it seems if we want to use the surfaceflinger gl
> composer, we need to mark the layers as client rendered in the
> validate function.

> >> I think the easiest and safe way is to just fallback to
> >> Composition::Client whenever the GLCompositor failed to initialize.
> >>
> >
> > I agree, this would only work out for the single plane case where you
end
> > up using client composition for everything.

> True, but maybe as a first step we simply fall back on the
> glcompositor, just so we have something displaying in that case (right
> now nothing gets displayed).

> > In the spirit of DRM what we would probably want is to atomic test a
> > composition, and if that fails we can still fallback to client or GL
> > compositor depending on its availability. And then in a far far away
> > future we might even do a few iterations simplifying our composition
until
> > it atomic tests correctly so we can still offload some "simple" parts
> > like the cursor.

> This sounds reasonable. I suspect it will take some heavier rework of
> the drm_hwcomposer to move such logic to the validate step.

> Marissa/Sean: Any objections here? Doing more planning in the validate
> step sounds like it aligns closer to the HWC2 interface goals, but I
> don't want to have to relearn-the-hard-way any lessons that resulted
> in the current mode of accept it all and sort it in present.


No objections, this needs to be done. As you mentioned, this is going to
require a good amount of code movement. I think what we're seeing here as
well, as with the writeback series, are growing pains. When this was
written, it was for HWC1 and the GLCompositor was the only alternate
compositor. Now that we're on HWC2 and discussing using writeback,
SurfaceFlinger, and possibly GLCompositor, we need something more robust.

Sean

> In the meantime I'll drop the flawed plane/layer allocation from this
> patch and resend.

> thanks
> -john
Alistair Strachan April 25, 2018, 6:15 p.m. | #6
Hi John,

On Tue, Apr 24, 2018 at 11:38 AM John Stultz <john.stultz@linaro.org> wrote:

> On Tue, Apr 24, 2018 at 3:34 AM, Stefan Schake <stschake@gmail.com> wrote:

> > On Tue, Apr 24, 2018 at 10:09 AM, Alexandru-Cosmin Gheorghe

> > <Alexandru-Cosmin.Gheorghe@arm.com> wrote:

> >> On Mon, Apr 23, 2018 at 05:06:44PM -0700, John Stultz wrote:

> >>> @@ -695,6 +704,15 @@ HWC2::Error

> DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,

> >>>          layer.set_validated_type(HWC2::Composition::Client);

> >>>          ++*num_types;

> >>>          break;

> >>> +      case HWC2::Composition::Device:

> >>> +        if (!compositor_.uses_GL() && !avail_planes) {

> >>

> >> Something is not entirely correct here, you can't assume just because

> >> you have planes available they can be used.

> >> E.g Layer has rotation, but the plane doesn't support it.

> >> This part is handled by the planning part in presentDisplay which

> >> falls back on GPU.

>

> Ah. Thanks for the correction here!

>

> This is part of the disconnect I have been having with the

> drm_hwcomposer logic. The plan/validate step doesn't really do either,

> instead it defers all the checking/planning to the set/present step.

> But unfortunately it seems if we want to use the surfaceflinger gl

> composer, we need to mark the layers as client rendered in the

> validate function.

>

> >> I think the easiest and safe way is to just fallback to

> >> Composition::Client whenever the GLCompositor failed to initialize.

> >>

> >

> > I agree, this would only work out for the single plane case where you end

> > up using client composition for everything.

>

> True, but maybe as a first step we simply fall back on the

> glcompositor, just so we have something displaying in that case (right

> now nothing gets displayed).

>

> > In the spirit of DRM what we would probably want is to atomic test a

> > composition, and if that fails we can still fallback to client or GL

> > compositor depending on its availability. And then in a far far away

> > future we might even do a few iterations simplifying our composition

> until

> > it atomic tests correctly so we can still offload some "simple" parts

> > like the cursor.

>

> This sounds reasonable. I suspect it will take some heavier rework of

> the drm_hwcomposer to move such logic to the validate step.

>

> Marissa/Sean: Any objections here? Doing more planning in the validate

> step sounds like it aligns closer to the HWC2 interface goals, but I

> don't want to have to relearn-the-hard-way any lessons that resulted

> in the current mode of accept it all and sort it in present.

>


I agree. This was the design goal behind HWC_GEOMETRY_CHANGED /
HWC2_PFN_GET_CHANGED_COMPOSITION_TYPES. The validate() function should know
that the composition can be set in HWC2_PFN_PRESENT_DISPLAY so there should
be no need for an internal GL fallback. This feedback to surfaceflinger
also allows for small state optimizations that can't be done in the
fallback.

I think validating compositions w/ atomic in kernel is a valid way to do it.

I would suggest that code is also refactored a little so that the
validation/planning could also be done in userspace, maybe by linking a
static library. This would allow drivers without a way to do it in kernel
to keep working.

In the meantime I'll drop the flawed plane/layer allocation from this
> patch and resend.

>

> thanks

> -john

>
<div dir="ltr">Hi John,<br><br><div class="gmail_quote"><div dir="ltr">On Tue, Apr 24, 2018 at 11:38 AM John Stultz &lt;<a href="mailto:john.stultz@linaro.org">john.stultz@linaro.org</a>&gt; wrote:<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">On Tue, Apr 24, 2018 at 3:34 AM, Stefan Schake &lt;<a href="mailto:stschake@gmail.com" target="_blank">stschake@gmail.com</a>&gt; wrote:<br>
&gt; On Tue, Apr 24, 2018 at 10:09 AM, Alexandru-Cosmin Gheorghe<br>
&gt; &lt;<a href="mailto:Alexandru-Cosmin.Gheorghe@arm.com" target="_blank">Alexandru-Cosmin.Gheorghe@arm.com</a>&gt; wrote:<br>
&gt;&gt; On Mon, Apr 23, 2018 at 05:06:44PM -0700, John Stultz wrote:<br>
&gt;&gt;&gt; @@ -695,6 +704,15 @@ HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,<br>
&gt;&gt;&gt;          layer.set_validated_type(HWC2::Composition::Client);<br>
&gt;&gt;&gt;          ++*num_types;<br>
&gt;&gt;&gt;          break;<br>
&gt;&gt;&gt; +      case HWC2::Composition::Device:<br>
&gt;&gt;&gt; +        if (!compositor_.uses_GL() &amp;&amp; !avail_planes) {<br>
&gt;&gt;<br>
&gt;&gt; Something is not entirely correct here, you can&#39;t assume just because<br>
&gt;&gt; you have planes available they can be used.<br>
&gt;&gt; E.g Layer has rotation, but the plane doesn&#39;t support it.<br>
&gt;&gt; This part is handled by the planning part in presentDisplay which<br>
&gt;&gt; falls back on GPU.<br>
<br>
Ah. Thanks for the correction here!<br>
<br>
This is part of the disconnect I have been having with the<br>
drm_hwcomposer logic. The plan/validate step doesn&#39;t really do either,<br>
instead it defers all the checking/planning to the set/present step.<br>
But unfortunately it seems if we want to use the surfaceflinger gl<br>
composer, we need to mark the layers as client rendered in the<br>
validate function.<br>
<br>
&gt;&gt; I think the easiest and safe way is to just fallback to<br>
&gt;&gt; Composition::Client whenever the GLCompositor failed to initialize.<br>
&gt;&gt;<br>
&gt;<br>
&gt; I agree, this would only work out for the single plane case where you end<br>
&gt; up using client composition for everything.<br>
<br>
True, but maybe as a first step we simply fall back on the<br>
glcompositor, just so we have something displaying in that case (right<br>
now nothing gets displayed).<br>
<br>
&gt; In the spirit of DRM what we would probably want is to atomic test a<br>
&gt; composition, and if that fails we can still fallback to client or GL<br>
&gt; compositor depending on its availability. And then in a far far away<br>
&gt; future we might even do a few iterations simplifying our composition until<br>
&gt; it atomic tests correctly so we can still offload some &quot;simple&quot; parts<br>
&gt; like the cursor.<br>
<br>
This sounds reasonable. I suspect it will take some heavier rework of<br>
the drm_hwcomposer to move such logic to the validate step.<br>
<br>
Marissa/Sean: Any objections here? Doing more planning in the validate<br>
step sounds like it aligns closer to the HWC2 interface goals, but I<br>
don&#39;t want to have to relearn-the-hard-way any lessons that resulted<br>
in the current mode of accept it all and sort it in present.<br></blockquote><div><br></div><div><span style="color:rgb(34,34,34);font-family:sans-serif;font-size:13px;font-style:normal;font-variant-ligatures:normal;font-variant-caps:normal;font-weight:400;letter-spacing:normal;text-align:start;text-indent:0px;text-transform:none;white-space:normal;word-spacing:0px;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline">I agree. This was the design goal behind HWC_GEOMETRY_CHANGED / HWC2_PFN_GET_CHANGED_COMPOSITION_TYPES. The validate() function should know that the composition can be set in HWC2_PFN_PRESENT_DISPLAY so there should be no need for an internal GL fallback. This feedback to surfaceflinger also allows for small state optimizations that can&#39;t be done in the fallback.</span></div><div><span style="color:rgb(34,34,34);font-family:sans-serif;font-size:13px;font-style:normal;font-variant-ligatures:normal;font-variant-caps:normal;font-weight:400;letter-spacing:normal;text-align:start;text-indent:0px;text-transform:none;white-space:normal;word-spacing:0px;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline"><br></span></div><div><span style="color:rgb(34,34,34);font-family:sans-serif;font-size:13px;font-style:normal;font-variant-ligatures:normal;font-variant-caps:normal;font-weight:400;letter-spacing:normal;text-align:start;text-indent:0px;text-transform:none;white-space:normal;word-spacing:0px;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline">I think validating compositions w/ atomic in kernel is a valid way to do it.</span></div><div><span style="color:rgb(34,34,34);font-family:sans-serif;font-size:13px;font-style:normal;font-variant-ligatures:normal;font-variant-caps:normal;font-weight:400;letter-spacing:normal;text-align:start;text-indent:0px;text-transform:none;white-space:normal;word-spacing:0px;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline"><br></span></div><div><span style="color:rgb(34,34,34);font-family:sans-serif;font-size:13px;font-style:normal;font-variant-ligatures:normal;font-variant-caps:normal;font-weight:400;letter-spacing:normal;text-align:start;text-indent:0px;text-transform:none;white-space:normal;word-spacing:0px;background-color:rgb(255,255,255);text-decoration-style:initial;text-decoration-color:initial;float:none;display:inline">I would suggest that code is also refactored a little so that the validation/planning could also be done in userspace, maybe by linking a static library. This would allow drivers without a way to do it in kernel to keep working.</span></div><div><br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
In the meantime I&#39;ll drop the flawed plane/layer allocation from this<br>
patch and resend.<br>
<br>
thanks<br>
-john<br>
</blockquote></div></div>

Patch

diff --git a/drmhwctwo.cpp b/drmhwctwo.cpp
index dfca1a6..437a439 100644
--- a/drmhwctwo.cpp
+++ b/drmhwctwo.cpp
@@ -686,6 +686,15 @@  HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
   supported(__func__);
   *num_types = 0;
   *num_requests = 0;
+  int avail_planes = primary_planes_.size() + overlay_planes_.size();
+
+  /*
+   * If more layers then planes, save one plane
+   * for client composited layers
+   */
+  if (avail_planes < layers_.size())
+	avail_planes--;
+
   for (std::pair<const hwc2_layer_t, DrmHwcTwo::HwcLayer> &l : layers_) {
     DrmHwcTwo::HwcLayer &layer = l.second;
     switch (layer.sf_type()) {
@@ -695,6 +704,15 @@  HWC2::Error DrmHwcTwo::HwcDisplay::ValidateDisplay(uint32_t *num_types,
         layer.set_validated_type(HWC2::Composition::Client);
         ++*num_types;
         break;
+      case HWC2::Composition::Device:
+        if (!compositor_.uses_GL() && !avail_planes) {
+          layer.set_validated_type(HWC2::Composition::Client);
+          ++*num_types;
+          break;
+        } else {
+	   avail_planes--;
+	}
+	/* fall through */
       default:
         layer.set_validated_type(layer.sf_type());
         break;