All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH] Optimise scrolling by avoiding function calls and aligned memory copy
@ 2009-11-30 10:10 Vladimir 'φ-coder/phcoder' Serbinenko
  2010-01-07 19:01 ` Robert Millan
  0 siblings, 1 reply; 2+ messages in thread
From: Vladimir 'φ-coder/phcoder' Serbinenko @ 2009-11-30 10:10 UTC (permalink / raw)
  To: The development of GRUB 2


[-- Attachment #1.1: Type: text/plain, Size: 153 bytes --]

Available in experimental. In QEMU benchmark scrolling 1000 lines
decreased from 72s to 32s.

-- 
Regards
Vladimir 'φ-coder/phcoder' Serbinenko


[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.2: scrollopt.diff --]
[-- Type: text/x-diff; name="scrollopt.diff", Size: 4901 bytes --]

=== added file 'ChangeLog.scrollopt'
--- ChangeLog.scrollopt	1970-01-01 00:00:00 +0000
+++ ChangeLog.scrollopt	2009-11-30 09:26:26 +0000
@@ -0,0 +1,4 @@
+2009-11-30  Vladimir Serbinenko  <phcoder@gmail.com>
+
+	* video/fb/video_fb.c (grub_video_fb_scroll): Optimise by avoiding
+	unnecessary calls.

=== modified file 'video/fb/video_fb.c'
--- video/fb/video_fb.c	2009-08-28 13:54:20 +0000
+++ video/fb/video_fb.c	2009-11-30 09:52:10 +0000
@@ -974,32 +974,83 @@
     {
       /* 3. Move data in render target.  */
       struct grub_video_fbblit_info target;
-      grub_uint8_t *src;
-      grub_uint8_t *dst;
-      int j;
+      int i, j;
+      int linedelta, linelen;
 
       target.mode_info = &render_target->mode_info;
       target.data = render_target->data;
 
-      /* Check vertical direction of the move.  */
-      if (dy <= 0)
-	/* 3a. Move data upwards.  */
-	for (j = 0; j < height; j++)
-	  {
-	    dst = grub_video_fb_get_video_ptr (&target, dst_x, dst_y + j);
-	    src = grub_video_fb_get_video_ptr (&target, src_x, src_y + j);
-	    grub_memmove (dst, src,
-			  width * target.mode_info->bytes_per_pixel);
-	  }
+      linedelta = target.mode_info->pitch
+	- width * target.mode_info->bytes_per_pixel;
+      linelen = width * target.mode_info->bytes_per_pixel;
+#define DO_SCROLL                                                    \
+      /* Check vertical direction of the move.  */                   \
+      if (dy < 0 || (dy == 0 && dx < 0))                             \
+	{                                                            \
+	  dst = (void *) grub_video_fb_get_video_ptr (&target,       \
+						      dst_x, dst_y); \
+	  src = (void *) grub_video_fb_get_video_ptr (&target,	     \
+						      src_x, src_y); \
+	  /* 3a. Move data upwards.  */                              \
+	  for (j = 0; j < height; j++)                               \
+	    {                                                        \
+	      for (i = 0; i < linelen; i++)                          \
+		*(dst++) = *(src++);	                             \
+	      dst += linedelta;                                      \
+	      src += linedelta;                                      \
+	    }							     \
+	}                                                            \
+      else                                                           \
+	{                                                            \
+	  /* 3b. Move data downwards.  */                            \
+	  dst = (void *) grub_video_fb_get_video_ptr (&target,	     \
+					     dst_x + width - 1,      \
+					     dst_y + height - 1);    \
+	  src = (void *) grub_video_fb_get_video_ptr (&target,	     \
+					     src_x + width - 1,      \
+					     src_y + height - 1);    \
+	  for (j = 0; j < height; j++)                               \
+	    {                                                        \
+	      for (i = 0; i < linelen; i++)                          \
+		*(dst--) = *(src--);                                 \
+	      dst -= linedelta;                                      \
+	      src -= linedelta;                                      \
+	    }                                                        \
+	}
+
+      /* If everything is aligned on 32-bit use 32-bit copy.  */
+      if ((grub_addr_t) grub_video_fb_get_video_ptr (&target, src_x, src_y)
+	  % sizeof (grub_uint32_t) == 0
+	  && (grub_addr_t) grub_video_fb_get_video_ptr (&target, dst_x, dst_y) 
+	  % sizeof (grub_uint32_t) == 0
+	  && linelen % sizeof (grub_uint32_t) == 0
+	  && linedelta % sizeof (grub_uint32_t) == 0)
+	{
+	  grub_uint32_t *src, *dst;
+	  linelen /= sizeof (grub_uint32_t);
+	  linedelta /= sizeof (grub_uint32_t);
+	  DO_SCROLL
+	}
+      /* If everything is aligned on 16-bit use 16-bit copy.  */
+      else if ((grub_addr_t) grub_video_fb_get_video_ptr (&target, src_x, src_y)
+	       % sizeof (grub_uint16_t) == 0
+	       && (grub_addr_t) grub_video_fb_get_video_ptr (&target,
+							     dst_x, dst_y) 
+	       % sizeof (grub_uint16_t) == 0
+	       && linelen % sizeof (grub_uint16_t) == 0
+	       && linedelta % sizeof (grub_uint16_t) == 0)
+	{
+	  grub_uint16_t *src, *dst;
+	  linelen /= sizeof (grub_uint16_t);
+	  linedelta /= sizeof (grub_uint16_t);
+	  DO_SCROLL
+	}
+      /* If not aligned at all use 8-bit copy.  */
       else
-	/* 3b. Move data downwards.  */
-	for (j = (height - 1); j >= 0; j--)
-	  {
-	    dst = grub_video_fb_get_video_ptr (&target, dst_x, dst_y + j);
-	    src = grub_video_fb_get_video_ptr (&target, src_x, src_y + j);
-	    grub_memmove (dst, src,
-			  width * target.mode_info->bytes_per_pixel);
-	  }
+	{
+	  grub_uint8_t *src, *dst;
+	  DO_SCROLL
+	}	
     }
 
   /* 4. Fill empty space with specified color.  In this implementation


[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 293 bytes --]

^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: [PATCH] Optimise scrolling by avoiding function calls and aligned memory copy
  2009-11-30 10:10 [PATCH] Optimise scrolling by avoiding function calls and aligned memory copy Vladimir 'φ-coder/phcoder' Serbinenko
@ 2010-01-07 19:01 ` Robert Millan
  0 siblings, 0 replies; 2+ messages in thread
From: Robert Millan @ 2010-01-07 19:01 UTC (permalink / raw)
  To: The development of GNU GRUB

On Mon, Nov 30, 2009 at 11:10:10AM +0100, Vladimir 'φ-coder/phcoder' Serbinenko wrote:
> Available in experimental. In QEMU benchmark scrolling 1000 lines
> decreased from 72s to 32s.

Please can you merge this in trunk?

-- 
Robert Millan

  "Be the change you want to see in the world" -- Gandhi



^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2010-01-07 19:01 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-11-30 10:10 [PATCH] Optimise scrolling by avoiding function calls and aligned memory copy Vladimir 'φ-coder/phcoder' Serbinenko
2010-01-07 19:01 ` Robert Millan

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.