[Mesa-dev] [PATCH v2] i965: Implement CopyTexSubImage2D via BLORP (and use it by default).
Kenneth Graunke
kenneth at whitecape.org
Mon Jan 28 23:42:04 PST 2013
On 01/28/2013 02:34 PM, Kenneth Graunke wrote:
> The BLT engine has many limitations. Currently, it can only blit
> X-tiled buffers (since we don't have a kernel API to whack the BLT
> tiling mode register), which means all depth/stencil operations get
> punted to meta code, which can be very CPU-intensive.
>
> Even if we used the BLT engine, it can't blit between buffers with
> different tiling modes, such as an X-tiled non-MSAA ARGB8888 texture
> and a Y-tiled CMS ARGB8888 renderbuffer. This is a fundamental
> limitation, and the only way around that is to use BLORP.
>
> Previously, BLORP only handled BlitFramebuffer. This patch adds an
> additional frontend for doing CopyTexSubImage. It also makes it the
> default. This is partly to increase testing and avoid hiding bugs,
> and partly because the BLORP path can already handle more cases. With
> trivial extensions, it should be able to handle everything the BLT can.
>
> This helps PlaneShift massively, which tries to CopyTexSubImage2D
> between depth buffers whenever a player casts a spell. Since these
> are Y-tiled, we hit meta and software ReadPixels paths, eating 99% CPU
> while delivering ~1 FPS. This is particularly bad in an MMO setting
> because people cast spells all the time.
>
> It also helps Xonotic in 4X MSAA mode. At default power management
> settings, I measured a 6.35138% +/- 0.672548% performance boost (n=5).
> (This data is from v1 of the patch.)
>
> No Piglit regressions on Ivybridge. I have not tested Sandybridge.
>
> v2: Create a fake intel_renderbuffer to wrap the destination texture
> image and then reuse do_blorp_blit rather than reimplementing most
> of it. Remove unnecessary clipping code and conditional rendering
> check.
>
> Cc: Paul Berry <stereotype441 at gmail.com>
> Cc: Chad Versace <chad.versace at linux.intel.com>
> ---
> src/mesa/drivers/dri/i965/brw_blorp_blit.cpp | 64 ++++++++++++++++++++++++++++
> src/mesa/drivers/dri/i965/brw_context.h | 8 ++++
> src/mesa/drivers/dri/intel/intel_fbo.c | 30 +++++++++++++
> src/mesa/drivers/dri/intel/intel_fbo.h | 4 ++
> src/mesa/drivers/dri/intel/intel_tex_copy.c | 32 ++++++++++----
> 5 files changed, 130 insertions(+), 8 deletions(-)
>
> diff --git a/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp b/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp
> index bc7916a..e5f12fe 100644
> --- a/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp
> +++ b/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp
> @@ -295,6 +295,70 @@ try_blorp_blit(struct intel_context *intel,
> return true;
> }
>
> +bool
> +brw_blorp_copytexsubimage(struct intel_context *intel,
> + struct gl_renderbuffer *src_rb,
> + struct gl_texture_image *dst_image,
> + int srcX0, int srcY0,
> + int dstX0, int dstY0,
> + int width, int height)
> +{
> + struct gl_context *ctx = &intel->ctx;
> +
> + /* BLORP is not supported before Gen6. */
> + if (intel->gen < 6)
> + return false;
> +
> + /* BLORP requires the formats to match. In the future, we should relax
> + * this for simple format mismatches like XRGB <-> ARGB.
> + */
> + if (_mesa_get_srgb_format_linear(src_rb->Format) !=
> + _mesa_get_srgb_format_linear(dst_image->TexFormat))
> + return false;
> +
> + /* Sync up the state of window system buffers. We need to do this before
> + * we go looking for the buffers.
> + */
> + intel_prepare_render(intel);
> +
> + int srcY1 = srcY0 + height;
> + int dstX1 = dstX0 + width;
> + int dstY1 = dstY0 + height;
> +
> + /* Source clipping shouldn't be necessary, since copytexsubimage (in
> + * src/mesa/main/teximage.c) calls _mesa_clip_copytexsubimage() which
> + * takes care of it.
> + *
> + * Destination clipping shouldn't be necessary since the restrictions on
> + * glCopyTexSubImage prevent the user from specifying a destination rectangle
> + * that falls outside the bounds of the destination texture.
> + * See error_check_subtexture_dimensions().
> + */
> +
> + /* Account for the fact that in the system framebuffer, the origin is at
> + * the lower left.
> + */
> + bool mirror_y = false;
> + if (_mesa_is_winsys_fbo(ctx->ReadBuffer)) {
> + GLint tmp = src_rb->Height - srcY0;
> + srcY0 = src_rb->Height - srcY1;
> + srcY1 = tmp;
> + mirror_y = true;
> + }
> +
> + /* Create a fake/wrapper renderbuffer to allow us to use do_blorp_blit(). */
> + struct intel_renderbuffer *dst_irb =
> + intel_create_fake_renderbuffer_wrapper(intel, dst_image);
> + if (!dst_irb)
> + return false;
Uh. I forgot to send out the prerequisite patch.
This one also doesn't delete the fake intel_renderbuffer.
Working on a v3. Consider this NAK'd.
More information about the mesa-dev
mailing list