[Mesa-dev] [PATCH] st/vdpau: use bicubic filter for scaling

Christian König deathsimple at vodafone.de
Mon Jun 20 09:07:02 UTC 2016


> I don't understand the compositor code fully yet. How can I create a 
> unscaled image with it?
You allocate a temporary surface with the original size of the input 
video surface. Then call vl_compositor_render() with the temporary 
surface instead of the real destination.

This is what we should actually do for the noise reduction and sharpness 
filter as well, but so far I was just to lazy to implement that. There 
is also a comment in the code about that in the right location if I 
remember correctly.

E.g. pipeline should be:
1. Normal compositor setup except dst clip rect setup.
2. Rendering the compositor to a temporary texture with the same size as 
the input image.
3. Apply noise reduction.
4. Apply sharpness filter.
5. Apply scaling and write the result to the real destination.

Regards,
Christian.

Am 18.06.2016 um 06:24 schrieb Nayan Deshmukh:
> Hi Christian,
>
> Thanks for the review.
>
> I don't understand the compositor code fully yet. How can I create a 
> unscaled image with it?
>
> Regards,
> Nayan.
>
> On Fri, Jun 17, 2016 at 9:15 PM, Christian König 
> <deathsimple at vodafone.de <mailto:deathsimple at vodafone.de>> wrote:
>
>     Really nice work. I now understand where your problem is with the
>     scaled surface.
>
>     Please see the further comments below.
>
>
>     Am 16.06.2016 um 20:15 schrieb Nayan Deshmukh:
>
>         v2: fix a typo and add a newline to code
>
>         Signed-off-by: Nayan Deshmukh <nayan26deshmukh at gmail.com
>         <mailto:nayan26deshmukh at gmail.com>>
>         ---
>           src/gallium/state_trackers/vdpau/mixer.c         | 53
>         +++++++++++++++++++++---
>           src/gallium/state_trackers/vdpau/vdpau_private.h | 6 +++
>           2 files changed, 54 insertions(+), 5 deletions(-)
>
>         diff --git a/src/gallium/state_trackers/vdpau/mixer.c
>         b/src/gallium/state_trackers/vdpau/mixer.c
>         index 65c3ce2..751c7e5 100644
>         --- a/src/gallium/state_trackers/vdpau/mixer.c
>         +++ b/src/gallium/state_trackers/vdpau/mixer.c
>         @@ -82,7 +82,6 @@ vlVdpVideoMixerCreate(VdpDevice device,
>                 switch (features[i]) {
>                 /* they are valid, but we doesn't support them */
>                 case VDP_VIDEO_MIXER_FEATURE_DEINTERLACE_TEMPORAL_SPATIAL:
>         -      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L2:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L3:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L4:
>         @@ -110,6 +109,9 @@ vlVdpVideoMixerCreate(VdpDevice device,
>                    vmixer->luma_key.supported = true;
>                    break;
>           +      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>         +         vmixer->bicubic.supported = true;
>         +         break;
>                 default: goto no_params;
>                 }
>              }
>         @@ -202,6 +204,11 @@ vlVdpVideoMixerDestroy(VdpVideoMixer mixer)
>         vl_matrix_filter_cleanup(vmixer->sharpness.filter);
>                 FREE(vmixer->sharpness.filter);
>              }
>         +
>         +   if (vmixer->bicubic.filter) {
>         + vl_bicubic_filter_cleanup(vmixer->bicubic.filter);
>         +      FREE(vmixer->bicubic.filter);
>         +   }
>              pipe_mutex_unlock(vmixer->device->mutex);
>              DeviceReference(&vmixer->device, NULL);
>           @@ -344,7 +351,7 @@ VdpStatus
>         vlVdpVideoMixerRender(VdpVideoMixer mixer,
>              }
>          vl_compositor_set_dst_clip(&vmixer->cstate,
>         RectToPipe(destination_rect, &clip));
>         -   if (!vmixer->noise_reduction.filter &&
>         !vmixer->sharpness.filter)
>         +   if (!vmixer->noise_reduction.filter &&
>         !vmixer->sharpness.filter && !vmixer->bicubic.filter)
>                 vlVdpSave4DelayedRendering(vmixer->device,
>         destination_surface, &vmixer->cstate);
>              else {
>                 vl_compositor_render(&vmixer->cstate, compositor,
>         dst->surface, &dst->dirty_area, true);
>         @@ -359,6 +366,10 @@ VdpStatus
>         vlVdpVideoMixerRender(VdpVideoMixer mixer,
>                 if (vmixer->sharpness.filter)
>          vl_matrix_filter_render(vmixer->sharpness.filter,
>          dst->sampler_view, dst->surface);
>         +
>         +      if (vmixer->bicubic.filter)
>         +  vl_bicubic_filter_render(vmixer->bicubic.filter,
>         +  dst->sampler_view, dst->surface);
>
>
>     What you do here is first using the compositor to merge and scale
>     the surfaces and then apply bicubic filtering on the already
>     scaled surface.
>
>     That is rather suboptimal. It would be better to let the
>     compositor create an unscaled image and then scale it using
>     bicubic filtering.
>
>     Regards,
>     Christian.
>
>
>              }
>              pipe_mutex_unlock(vmixer->device->mutex);
>           @@ -461,6 +472,28 @@
>         vlVdpVideoMixerUpdateSharpnessFilter(vlVdpVideoMixer *vmixer)
>           }
>             /**
>         + * Update the bicubic filter
>         + */
>         +static void
>         +vlVdpVideoMixerUpdateBicubicFilter(vlVdpVideoMixer *vmixer)
>         +{
>         +   assert(vmixer);
>         +
>         +   /* if present remove the old filter first */
>         +   if (vmixer->bicubic.filter) {
>         + vl_bicubic_filter_cleanup(vmixer->bicubic.filter);
>         +      FREE(vmixer->bicubic.filter);
>         +      vmixer->bicubic.filter = NULL;
>         +   }
>         +   /* and create a new filter as needed */
>         +   if (vmixer->bicubic.enabled) {
>         +      vmixer->bicubic.filter = MALLOC(sizeof(struct
>         vl_bicubic_filter));
>         + vl_bicubic_filter_init(vmixer->bicubic.filter,
>         vmixer->device->context,
>         +                            vmixer->video_width,
>         vmixer->video_height);
>         +   }
>         +}
>         +
>         +/**
>            * Retrieve whether features were requested at creation time.
>            */
>           VdpStatus
>         @@ -483,7 +516,6 @@
>         vlVdpVideoMixerGetFeatureSupport(VdpVideoMixer mixer,
>                 switch (features[i]) {
>                 /* they are valid, but we doesn't support them */
>                 case VDP_VIDEO_MIXER_FEATURE_DEINTERLACE_TEMPORAL_SPATIAL:
>         -      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L2:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L3:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L4:
>         @@ -512,6 +544,10 @@
>         vlVdpVideoMixerGetFeatureSupport(VdpVideoMixer mixer,
>                    feature_supports[i] = vmixer->luma_key.supported;
>                    break;
>           +      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>         +         feature_supports[i] = vmixer->bicubic.supported;
>         +         break;
>         +
>                 default:
>                    return VDP_STATUS_INVALID_VIDEO_MIXER_FEATURE;
>                 }
>         @@ -544,7 +580,6 @@
>         vlVdpVideoMixerSetFeatureEnables(VdpVideoMixer mixer,
>                 switch (features[i]) {
>                 /* they are valid, but we doesn't support them */
>                 case VDP_VIDEO_MIXER_FEATURE_DEINTERLACE_TEMPORAL_SPATIAL:
>         -      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L2:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L3:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L4:
>         @@ -578,6 +613,11 @@
>         vlVdpVideoMixerSetFeatureEnables(VdpVideoMixer mixer,
>          vmixer->luma_key.luma_min, vmixer->luma_key.luma_max);
>                    break;
>           +      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>         +         vmixer->bicubic.enabled = feature_enables[i];
>         +         vlVdpVideoMixerUpdateBicubicFilter(vmixer);
>         +         break;
>         +
>                 default:
>          pipe_mutex_unlock(vmixer->device->mutex);
>                    return VDP_STATUS_INVALID_VIDEO_MIXER_FEATURE;
>         @@ -612,7 +652,6 @@
>         vlVdpVideoMixerGetFeatureEnables(VdpVideoMixer mixer,
>                 /* they are valid, but we doesn't support them */
>                 case VDP_VIDEO_MIXER_FEATURE_DEINTERLACE_TEMPORAL:
>                 case VDP_VIDEO_MIXER_FEATURE_DEINTERLACE_TEMPORAL_SPATIAL:
>         -      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L2:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L3:
>                 case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L4:
>         @@ -636,6 +675,10 @@
>         vlVdpVideoMixerGetFeatureEnables(VdpVideoMixer mixer,
>                    feature_enables[i] = vmixer->luma_key.enabled;
>                    break;
>           +      case VDP_VIDEO_MIXER_FEATURE_HIGH_QUALITY_SCALING_L1:
>         +         feature_enables[i] = vmixer->bicubic.enabled;
>         +         break;
>         +
>                 default:
>                    return VDP_STATUS_INVALID_VIDEO_MIXER_FEATURE;
>                 }
>         diff --git a/src/gallium/state_trackers/vdpau/vdpau_private.h
>         b/src/gallium/state_trackers/vdpau/vdpau_private.h
>         index 8673c6a..bcd4bb1 100644
>         --- a/src/gallium/state_trackers/vdpau/vdpau_private.h
>         +++ b/src/gallium/state_trackers/vdpau/vdpau_private.h
>         @@ -45,6 +45,7 @@
>           #include "os/os_thread.h"
>             #include "vl/vl_video_buffer.h"
>         +#include "vl/vl_bicubic_filter.h"
>           #include "vl/vl_compositor.h"
>           #include "vl/vl_csc.h"
>           #include "vl/vl_deint_filter.h"
>         @@ -373,6 +374,11 @@ typedef struct
>              } deint;
>                struct {
>         +         bool supported, enabled;
>         +         struct vl_bicubic_filter *filter;
>         +   } bicubic;
>         +
>         +   struct {
>                 bool supported, enabled;
>                 unsigned level;
>                 struct vl_median_filter *filter;
>
>
>

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.freedesktop.org/archives/mesa-dev/attachments/20160620/82857613/attachment-0001.html>


More information about the mesa-dev mailing list