vl: Add some query methods to pipe_video_context and use them.
authorYounes Manton <younes.m@gmail.com>
Sat, 13 Mar 2010 00:03:37 +0000 (19:03 -0500)
committerYounes Manton <younes.m@gmail.com>
Sat, 13 Mar 2010 00:03:37 +0000 (19:03 -0500)
src/gallium/drivers/softpipe/sp_video_context.c
src/gallium/include/pipe/p_video_context.h
src/gallium/state_trackers/xorg/xvmc/surface.c

index 7850908b1344505200fe0d0effad6008e8d3f932..9d75a1e508f3d1dd44eceb88bf7135088d582594 100644 (file)
@@ -59,6 +59,48 @@ sp_mpeg12_destroy(struct pipe_video_context *vpipe)
    FREE(ctx);
 }
 
+static int
+sp_mpeg12_get_param(struct pipe_video_context *vpipe, int param)
+{
+   struct sp_mpeg12_context *ctx = (struct sp_mpeg12_context*)vpipe;
+
+   assert(vpipe);
+
+   switch (param) {
+      case PIPE_CAP_NPOT_TEXTURES:
+         /* XXX: Temporary; not all paths are NPOT-tested */
+#if 0
+         return ctx->pipe->screen->get_param(ctx->pipe->screen, param);
+#endif
+         return FALSE;
+      case PIPE_CAP_DECODE_TARGET_PREFERRED_FORMAT:
+         return PIPE_FORMAT_AYUV;
+      default:
+      {
+         debug_printf("Softpipe: Unknown PIPE_CAP %d\n", param);
+         return 0;
+      }
+   }
+}
+
+static boolean
+sp_mpeg12_is_format_supported(struct pipe_video_context *vpipe,
+                              enum pipe_format format,
+                              unsigned usage,
+                              unsigned geom)
+{
+   struct sp_mpeg12_context *ctx = (struct sp_mpeg12_context*)vpipe;
+
+   assert(vpipe);
+
+   /* XXX: Temporary; not all paths are NPOT-tested */
+   if (geom & PIPE_TEXTURE_GEOM_NON_POWER_OF_TWO)
+      return FALSE;
+
+   return ctx->pipe->screen->is_format_supported(ctx->pipe->screen, PIPE_TEXTURE_2D,
+                                                 format, usage, geom);
+}
+
 static void
 sp_mpeg12_decode_macroblocks(struct pipe_video_context *vpipe,
                              struct pipe_surface *past,
@@ -297,6 +339,8 @@ sp_mpeg12_create(struct pipe_context *pipe, enum pipe_video_profile profile,
 
    ctx->base.screen = pipe->screen;
    ctx->base.destroy = sp_mpeg12_destroy;
+   ctx->base.get_param = sp_mpeg12_get_param;
+   ctx->base.is_format_supported = sp_mpeg12_is_format_supported;
    ctx->base.decode_macroblocks = sp_mpeg12_decode_macroblocks;
    ctx->base.render_picture = sp_mpeg12_render_picture;
    ctx->base.surface_fill = sp_mpeg12_surface_fill;
index f9dc625c7d7b9119efcbdf0b22640ad59d832992..d90b667de6c5e01bf10bb616ca4cc51aadfc5b54 100644 (file)
@@ -34,6 +34,9 @@ extern "C" {
 
 #include <pipe/p_video_state.h>
 
+/* XXX: Move to an appropriate place */
+#define PIPE_CAP_DECODE_TARGET_PREFERRED_FORMAT 256
+
 struct pipe_screen;
 struct pipe_buffer;
 struct pipe_surface;
@@ -54,6 +57,21 @@ struct pipe_video_context
 
    void *priv; /**< context private data (for DRI for example) */
 
+   /**
+    * Query an integer-valued capability/parameter/limit
+    * \param param  one of PIPE_CAP_x
+    */
+   int (*get_param)(struct pipe_video_context *vpipe, int param);
+
+   /**
+    * Check if the given pipe_format is supported as a texture or
+    * drawing surface.
+    */
+   boolean (*is_format_supported)(struct pipe_video_context *vpipe,
+                                  enum pipe_format format,
+                                  unsigned usage,
+                                  unsigned geom);
+
    void (*destroy)(struct pipe_video_context *vpipe);
 
    /**
index 354c257a806447a90dd9551c1cf0ccb714e34eed..998a7af0e95b63245fd223598f9ac10561662d2f 100644 (file)
@@ -211,12 +211,23 @@ Status XvMCCreateSurface(Display *dpy, XvMCContext *context, XvMCSurface *surfac
 
    memset(&template, 0, sizeof(struct pipe_texture));
    template.target = PIPE_TEXTURE_2D;
-   /* XXX: Let the pipe_video_context choose whatever format it likes to render to */
-   template.format = PIPE_FORMAT_AYUV;
+   template.format = (enum pipe_format)vpipe->get_param(vpipe, PIPE_CAP_DECODE_TARGET_PREFERRED_FORMAT);
    template.last_level = 0;
-   /* XXX: vl_mpeg12_mc_renderer expects this when it's initialized with pot_buffers=true, clean this up */
-   template.width0 = util_next_power_of_two(context->width);
-   template.height0 = util_next_power_of_two(context->height);
+   if (vpipe->is_format_supported(vpipe, template.format,
+                                  PIPE_TEXTURE_USAGE_SAMPLER |
+                                  PIPE_TEXTURE_USAGE_RENDER_TARGET,
+                                  PIPE_TEXTURE_GEOM_NON_POWER_OF_TWO)) {
+      template.width0 = context->width;
+      template.height0 = context->height;
+   }
+   else {
+      assert(vpipe->is_format_supported(vpipe, template.format,
+                                       PIPE_TEXTURE_USAGE_SAMPLER |
+                                       PIPE_TEXTURE_USAGE_RENDER_TARGET,
+                                       PIPE_TEXTURE_GEOM_NON_SQUARE));
+      template.width0 = util_next_power_of_two(context->width);
+      template.height0 = util_next_power_of_two(context->height);
+   }
    template.depth0 = 1;
    template.tex_usage = PIPE_TEXTURE_USAGE_SAMPLER | PIPE_TEXTURE_USAGE_RENDER_TARGET;
    vsfc_tex = vpipe->screen->texture_create(vpipe->screen, &template);