mirror of
				https://git.proxmox.com/git/grub2
				synced 2025-11-04 06:47:23 +00:00 
			
		
		
		
	This tries to catch all cases where grub_cpu_to_XXX was used for constant expressions (including sizeof).
		
			
				
	
	
		
			814 lines
		
	
	
		
			20 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			814 lines
		
	
	
		
			20 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
/*
 | 
						|
 *  GRUB  --  GRand Unified Bootloader
 | 
						|
 *  Copyright (C) 2013 Free Software Foundation, Inc.
 | 
						|
 *
 | 
						|
 *  GRUB is free software: you can redistribute it and/or modify
 | 
						|
 *  it under the terms of the GNU General Public License as published by
 | 
						|
 *  the Free Software Foundation, either version 3 of the License, or
 | 
						|
 *  (at your option) any later version.
 | 
						|
 *
 | 
						|
 *  GRUB is distributed in the hope that it will be useful,
 | 
						|
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 | 
						|
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 | 
						|
 *  GNU General Public License for more details.
 | 
						|
 *
 | 
						|
 *  You should have received a copy of the GNU General Public License
 | 
						|
 *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
 | 
						|
 */
 | 
						|
 | 
						|
/* All tests need to include test.h for GRUB testing framework.  */
 | 
						|
 | 
						|
#include <config.h>
 | 
						|
 | 
						|
#include <grub/test.h>
 | 
						|
#include <grub/dl.h>
 | 
						|
#include <grub/video.h>
 | 
						|
#include <grub/lib/crc.h>
 | 
						|
#include <grub/mm.h>
 | 
						|
#include <grub/term.h>
 | 
						|
#ifdef GRUB_MACHINE_EMU
 | 
						|
#include <grub/emu/hostdisk.h>
 | 
						|
#include <grub/emu/misc.h>
 | 
						|
#endif
 | 
						|
 | 
						|
GRUB_MOD_LICENSE ("GPLv3+");
 | 
						|
 | 
						|
static int ctr;
 | 
						|
static int nchk;
 | 
						|
static char *basename;
 | 
						|
static const grub_uint32_t *checksums;
 | 
						|
static struct grub_video_mode_info capt_mode_info;
 | 
						|
 | 
						|
struct grub_video_mode_info grub_test_video_modes[GRUB_TEST_VIDEO_ALL_N_MODES] = {
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 640,
 | 
						|
    .mode_type = GRUB_VIDEO_MODE_TYPE_INDEX_COLOR,
 | 
						|
    .bpp = 8,
 | 
						|
    .bytes_per_pixel = 1,
 | 
						|
    .number_of_colors = GRUB_VIDEO_FBSTD_NUMCOLORS
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 800,
 | 
						|
    .mode_type = GRUB_VIDEO_MODE_TYPE_INDEX_COLOR,
 | 
						|
    .bpp = 8,
 | 
						|
    .bytes_per_pixel = 1,
 | 
						|
    .number_of_colors = GRUB_VIDEO_FBSTD_NUMCOLORS
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 1024,
 | 
						|
    .mode_type = GRUB_VIDEO_MODE_TYPE_INDEX_COLOR,
 | 
						|
    .bpp = 8,
 | 
						|
    .bytes_per_pixel = 1,
 | 
						|
    .number_of_colors = GRUB_VIDEO_FBSTD_NUMCOLORS
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 640 * 4,
 | 
						|
    GRUB_VIDEO_MI_RGBA8888()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 800 * 4,
 | 
						|
    GRUB_VIDEO_MI_RGBA8888()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 1024 * 4,
 | 
						|
    GRUB_VIDEO_MI_RGBA8888()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 2560,
 | 
						|
    .height = 1440,
 | 
						|
    .pitch = 2560 * 4,
 | 
						|
    GRUB_VIDEO_MI_RGBA8888()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 640,
 | 
						|
    .mode_type = GRUB_VIDEO_MODE_TYPE_INDEX_COLOR,
 | 
						|
    .bpp = 8,
 | 
						|
    .bytes_per_pixel = 1,
 | 
						|
    .number_of_colors = GRUB_VIDEO_FBSTD_EXT_NUMCOLORS
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 800,
 | 
						|
    .mode_type = GRUB_VIDEO_MODE_TYPE_INDEX_COLOR,
 | 
						|
    .bpp = 8,
 | 
						|
    .bytes_per_pixel = 1,
 | 
						|
    .number_of_colors = GRUB_VIDEO_FBSTD_EXT_NUMCOLORS
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 1024,
 | 
						|
    .mode_type = GRUB_VIDEO_MODE_TYPE_INDEX_COLOR,
 | 
						|
    .bpp = 8,
 | 
						|
    .bytes_per_pixel = 1,
 | 
						|
    .number_of_colors = GRUB_VIDEO_FBSTD_EXT_NUMCOLORS
 | 
						|
  },
 | 
						|
 | 
						|
 | 
						|
 | 
						|
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 1280,
 | 
						|
    GRUB_VIDEO_MI_RGB555 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 1600,
 | 
						|
    GRUB_VIDEO_MI_RGB555 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 2048,
 | 
						|
    GRUB_VIDEO_MI_RGB555 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 1280,
 | 
						|
    GRUB_VIDEO_MI_RGB565 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 1600,
 | 
						|
    GRUB_VIDEO_MI_RGB565 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 2048,
 | 
						|
    GRUB_VIDEO_MI_RGB565 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 640 * 3,
 | 
						|
    GRUB_VIDEO_MI_RGB888 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 800 * 3,
 | 
						|
    GRUB_VIDEO_MI_RGB888 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 1024 * 3,
 | 
						|
    GRUB_VIDEO_MI_RGB888 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 1280,
 | 
						|
    GRUB_VIDEO_MI_BGR555 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 1600,
 | 
						|
    GRUB_VIDEO_MI_BGR555 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 2048,
 | 
						|
    GRUB_VIDEO_MI_BGR555 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 1280,
 | 
						|
    GRUB_VIDEO_MI_BGR565 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 1600,
 | 
						|
    GRUB_VIDEO_MI_BGR565 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 2048,
 | 
						|
    GRUB_VIDEO_MI_BGR565 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 640 * 3,
 | 
						|
    GRUB_VIDEO_MI_BGR888 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 800 * 3,
 | 
						|
    GRUB_VIDEO_MI_BGR888 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 1024 * 3,
 | 
						|
    GRUB_VIDEO_MI_BGR888 ()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 640,
 | 
						|
    .height = 480,
 | 
						|
    .pitch = 640 * 4,
 | 
						|
    GRUB_VIDEO_MI_BGRA8888()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 800,
 | 
						|
    .height = 600,
 | 
						|
    .pitch = 800 * 4,
 | 
						|
    GRUB_VIDEO_MI_BGRA8888()
 | 
						|
  },
 | 
						|
  {
 | 
						|
    .width = 1024,
 | 
						|
    .height = 768,
 | 
						|
    .pitch = 1024 * 4,
 | 
						|
    GRUB_VIDEO_MI_BGRA8888()
 | 
						|
  },
 | 
						|
};
 | 
						|
 | 
						|
#ifdef GRUB_MACHINE_EMU
 | 
						|
#include <grub/emu/hostfile.h>
 | 
						|
 | 
						|
struct bmp_header
 | 
						|
{
 | 
						|
  grub_uint8_t magic[2];
 | 
						|
  grub_uint32_t filesize;
 | 
						|
  grub_uint32_t reserved;
 | 
						|
  grub_uint32_t bmp_off;
 | 
						|
  grub_uint32_t head_size;
 | 
						|
  grub_uint16_t width;
 | 
						|
  grub_uint16_t height;
 | 
						|
  grub_uint16_t planes;
 | 
						|
  grub_uint16_t bpp;
 | 
						|
} GRUB_PACKED;
 | 
						|
 | 
						|
static void
 | 
						|
grub_video_capture_write_bmp (const char *fname,
 | 
						|
			      void *ptr,
 | 
						|
			      const struct grub_video_mode_info *mode_info)
 | 
						|
{
 | 
						|
  grub_util_fd_t fd = grub_util_fd_open (fname, GRUB_UTIL_FD_O_WRONLY | GRUB_UTIL_FD_O_CREATTRUNC);
 | 
						|
  struct bmp_header head;
 | 
						|
 | 
						|
  if (!GRUB_UTIL_FD_IS_VALID (fd))
 | 
						|
    {
 | 
						|
      grub_printf (_("cannot open `%s': %s"),
 | 
						|
		   fname, grub_util_fd_strerror ());
 | 
						|
    }
 | 
						|
 | 
						|
  grub_memset (&head, 0, sizeof (head));
 | 
						|
 | 
						|
  head.magic[0] = 'B';
 | 
						|
  head.magic[1] = 'M';
 | 
						|
 | 
						|
  if (mode_info->mode_type & GRUB_VIDEO_MODE_TYPE_RGB)
 | 
						|
    {
 | 
						|
      head.filesize = grub_cpu_to_le32 (sizeof (head) + mode_info->width * mode_info->height * 3);
 | 
						|
      head.bmp_off = grub_cpu_to_le32_compile_time (sizeof (head));
 | 
						|
      head.bpp = grub_cpu_to_le16_compile_time (24);
 | 
						|
    }
 | 
						|
  else
 | 
						|
    {
 | 
						|
      head.filesize = grub_cpu_to_le32 (sizeof (head) + 3 * 256 + mode_info->width * mode_info->height);
 | 
						|
      head.bmp_off = grub_cpu_to_le32_compile_time (sizeof (head) + 3 * 256);
 | 
						|
      head.bpp = grub_cpu_to_le16_compile_time (8);
 | 
						|
    }
 | 
						|
  head.head_size = grub_cpu_to_le32_compile_time (sizeof (head) - 14);
 | 
						|
  head.width = grub_cpu_to_le16 (mode_info->width);
 | 
						|
  head.height = grub_cpu_to_le16 (mode_info->height);
 | 
						|
  head.planes = grub_cpu_to_le16_compile_time (1);
 | 
						|
 | 
						|
  head.width = grub_cpu_to_le16 (mode_info->width);
 | 
						|
  head.height = grub_cpu_to_le16 (mode_info->height);
 | 
						|
 | 
						|
  grub_util_fd_write (fd, (char *) &head, sizeof (head));
 | 
						|
 | 
						|
  if (!(mode_info->mode_type & GRUB_VIDEO_MODE_TYPE_RGB))
 | 
						|
    {
 | 
						|
      struct grub_video_palette_data palette_data[256];
 | 
						|
      int i;
 | 
						|
      int palette_len = mode_info->number_of_colors;
 | 
						|
      grub_memset (palette_data, 0, sizeof (palette_data));
 | 
						|
      if (palette_len > 256)
 | 
						|
	palette_len = 256;
 | 
						|
      grub_video_get_palette (0, palette_len, palette_data);
 | 
						|
      for (i = 0; i < 256; i++)
 | 
						|
	{
 | 
						|
	  grub_uint8_t r, g, b;
 | 
						|
	  r = palette_data[i].r;
 | 
						|
	  g = palette_data[i].g;
 | 
						|
	  b = palette_data[i].b;
 | 
						|
 | 
						|
	  grub_util_fd_write (fd, (char *) &b, 1);
 | 
						|
	  grub_util_fd_write (fd, (char *) &g, 1);
 | 
						|
	  grub_util_fd_write (fd, (char *) &r, 1);
 | 
						|
	}
 | 
						|
    }
 | 
						|
 | 
						|
  /* This does essentialy the same as some fbblit functions yet using
 | 
						|
     them would mean testing them against themselves so keep this
 | 
						|
     implemetation separate.  */
 | 
						|
  switch (mode_info->bytes_per_pixel)
 | 
						|
    {
 | 
						|
    case 4:
 | 
						|
      {
 | 
						|
	grub_uint8_t *buffer = xmalloc (mode_info->width * 3);
 | 
						|
	grub_uint32_t rmask = ((1 << mode_info->red_mask_size) - 1);
 | 
						|
	grub_uint32_t gmask = ((1 << mode_info->green_mask_size) - 1);
 | 
						|
	grub_uint32_t bmask = ((1 << mode_info->blue_mask_size) - 1);
 | 
						|
	int rshift = mode_info->red_field_pos;
 | 
						|
	int gshift = mode_info->green_field_pos;
 | 
						|
	int bshift = mode_info->blue_field_pos;
 | 
						|
	int mulrshift = (8 - mode_info->red_mask_size);
 | 
						|
	int mulgshift = (8 - mode_info->green_mask_size);
 | 
						|
	int mulbshift = (8 - mode_info->blue_mask_size);
 | 
						|
	int y;
 | 
						|
 | 
						|
	for (y = mode_info->height - 1; y >= 0; y--)
 | 
						|
	  {
 | 
						|
	    grub_uint32_t *iptr = (grub_uint32_t *) ptr + (mode_info->pitch / 4) * y;
 | 
						|
	    int x;
 | 
						|
	    grub_uint8_t *optr = buffer;
 | 
						|
	    for (x = 0; x < (int) mode_info->width; x++)
 | 
						|
	      {
 | 
						|
		grub_uint32_t val = *iptr++;
 | 
						|
		*optr++ = ((val >> bshift) & bmask) << mulbshift;
 | 
						|
		*optr++ = ((val >> gshift) & gmask) << mulgshift;
 | 
						|
		*optr++ = ((val >> rshift) & rmask) << mulrshift;
 | 
						|
	      }
 | 
						|
	    grub_util_fd_write (fd, (char *) buffer, mode_info->width * 3);
 | 
						|
	  }
 | 
						|
	grub_free (buffer);
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    case 3:
 | 
						|
      {
 | 
						|
	grub_uint8_t *buffer = xmalloc (mode_info->width * 3);
 | 
						|
	grub_uint32_t rmask = ((1 << mode_info->red_mask_size) - 1);
 | 
						|
	grub_uint32_t gmask = ((1 << mode_info->green_mask_size) - 1);
 | 
						|
	grub_uint32_t bmask = ((1 << mode_info->blue_mask_size) - 1);
 | 
						|
	int rshift = mode_info->red_field_pos;
 | 
						|
	int gshift = mode_info->green_field_pos;
 | 
						|
	int bshift = mode_info->blue_field_pos;
 | 
						|
	int mulrshift = (8 - mode_info->red_mask_size);
 | 
						|
	int mulgshift = (8 - mode_info->green_mask_size);
 | 
						|
	int mulbshift = (8 - mode_info->blue_mask_size);
 | 
						|
	int y;
 | 
						|
 | 
						|
	for (y = mode_info->height - 1; y >= 0; y--)
 | 
						|
	  {
 | 
						|
	    grub_uint8_t *iptr = ((grub_uint8_t *) ptr + mode_info->pitch * y);
 | 
						|
	    int x;
 | 
						|
	    grub_uint8_t *optr = buffer;
 | 
						|
	    for (x = 0; x < (int) mode_info->width; x++)
 | 
						|
	      {
 | 
						|
		grub_uint32_t val = 0;
 | 
						|
#ifdef GRUB_CPU_WORDS_BIGENDIAN
 | 
						|
		val |= *iptr++ << 16;
 | 
						|
		val |= *iptr++ << 8;
 | 
						|
		val |= *iptr++;
 | 
						|
#else
 | 
						|
		val |= *iptr++;
 | 
						|
		val |= *iptr++ << 8;
 | 
						|
		val |= *iptr++ << 16;
 | 
						|
#endif
 | 
						|
		*optr++ = ((val >> bshift) & bmask) << mulbshift;
 | 
						|
		*optr++ = ((val >> gshift) & gmask) << mulgshift;
 | 
						|
		*optr++ = ((val >> rshift) & rmask) << mulrshift;
 | 
						|
	      }
 | 
						|
	    grub_util_fd_write (fd, (char *) buffer, mode_info->width * 3);
 | 
						|
	  }
 | 
						|
	grub_free (buffer);
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    case 2:
 | 
						|
      {
 | 
						|
	grub_uint8_t *buffer = xmalloc (mode_info->width * 3);
 | 
						|
	grub_uint16_t rmask = ((1 << mode_info->red_mask_size) - 1);
 | 
						|
	grub_uint16_t gmask = ((1 << mode_info->green_mask_size) - 1);
 | 
						|
	grub_uint16_t bmask = ((1 << mode_info->blue_mask_size) - 1);
 | 
						|
	int rshift = mode_info->red_field_pos;
 | 
						|
	int gshift = mode_info->green_field_pos;
 | 
						|
	int bshift = mode_info->blue_field_pos;
 | 
						|
	int mulrshift = (8 - mode_info->red_mask_size);
 | 
						|
	int mulgshift = (8 - mode_info->green_mask_size);
 | 
						|
	int mulbshift = (8 - mode_info->blue_mask_size);
 | 
						|
	int y;
 | 
						|
 | 
						|
	for (y = mode_info->height - 1; y >= 0; y--)
 | 
						|
	  {
 | 
						|
	    grub_uint16_t *iptr = (grub_uint16_t *) ptr + (mode_info->pitch / 2) * y;
 | 
						|
	    int x;
 | 
						|
	    grub_uint8_t *optr = buffer;
 | 
						|
	    for (x = 0; x < (int) mode_info->width; x++)
 | 
						|
	      {
 | 
						|
		grub_uint16_t val = *iptr++;
 | 
						|
		*optr++ = ((val >> bshift) & bmask) << mulbshift;
 | 
						|
		*optr++ = ((val >> gshift) & gmask) << mulgshift;
 | 
						|
		*optr++ = ((val >> rshift) & rmask) << mulrshift;
 | 
						|
	      }
 | 
						|
	    grub_util_fd_write (fd, (char *) buffer, mode_info->width * 3);
 | 
						|
	  }
 | 
						|
	grub_free (buffer);
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    case 1:
 | 
						|
      {
 | 
						|
	int y;
 | 
						|
 | 
						|
	for (y = mode_info->height - 1; y >= 0; y--)
 | 
						|
	  grub_util_fd_write (fd, ((char *) ptr + mode_info->pitch * y),
 | 
						|
			      mode_info->width);
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    }
 | 
						|
  grub_util_fd_close (fd);
 | 
						|
}
 | 
						|
 | 
						|
#endif
 | 
						|
 | 
						|
const char *
 | 
						|
grub_video_checksum_get_modename (void)
 | 
						|
{
 | 
						|
  static char buf[40];
 | 
						|
  if (capt_mode_info.mode_type & GRUB_VIDEO_MODE_TYPE_INDEX_COLOR)
 | 
						|
    {
 | 
						|
      grub_snprintf (buf, sizeof (buf), "i%d", capt_mode_info.number_of_colors);
 | 
						|
      return buf;
 | 
						|
    }
 | 
						|
  if (capt_mode_info.red_field_pos == 0)
 | 
						|
    {
 | 
						|
      grub_snprintf (buf, sizeof (buf), "bgra%d%d%d%d", capt_mode_info.blue_mask_size,
 | 
						|
		     capt_mode_info.green_mask_size,
 | 
						|
		     capt_mode_info.red_mask_size,
 | 
						|
		     capt_mode_info.reserved_mask_size);
 | 
						|
      return buf;
 | 
						|
    }
 | 
						|
  grub_snprintf (buf, sizeof (buf), "rgba%d%d%d%d", capt_mode_info.red_mask_size,
 | 
						|
		 capt_mode_info.green_mask_size,
 | 
						|
		 capt_mode_info.blue_mask_size,
 | 
						|
		 capt_mode_info.reserved_mask_size);
 | 
						|
  return buf;
 | 
						|
}
 | 
						|
 | 
						|
#define GENERATE_MODE 1
 | 
						|
//#define SAVE_ALL_IMAGES
 | 
						|
//#define COLLECT_TIME_STATISTICS 1
 | 
						|
 | 
						|
#if defined (GENERATE_MODE) && defined (GRUB_MACHINE_EMU)
 | 
						|
grub_util_fd_t genfd = GRUB_UTIL_FD_INVALID;
 | 
						|
#endif
 | 
						|
 | 
						|
#include <grub/time.h>
 | 
						|
 | 
						|
static void
 | 
						|
write_time (void)
 | 
						|
{
 | 
						|
#if defined (GRUB_MACHINE_EMU) && defined (COLLECT_TIME_STATISTICS)
 | 
						|
  char buf[60];
 | 
						|
  static grub_uint64_t prev;
 | 
						|
  grub_uint64_t cur;
 | 
						|
  static grub_util_fd_t tmrfd = GRUB_UTIL_FD_INVALID;
 | 
						|
  if (!GRUB_UTIL_FD_IS_VALID (tmrfd))
 | 
						|
    tmrfd = grub_util_fd_open ("time.txt", GRUB_UTIL_FD_O_WRONLY
 | 
						|
			       | GRUB_UTIL_FD_O_CREATTRUNC);
 | 
						|
 | 
						|
  cur = grub_util_get_cpu_time_ms ();
 | 
						|
  grub_snprintf (buf, sizeof (buf), "%s_%dx%dx%s:%d: %" PRIuGRUB_UINT64_T " ms\n",
 | 
						|
		 basename, 			
 | 
						|
		 capt_mode_info.width,
 | 
						|
		 capt_mode_info.height, 
 | 
						|
		 grub_video_checksum_get_modename (), ctr,
 | 
						|
		 cur - prev);
 | 
						|
  prev = cur;
 | 
						|
  if (GRUB_UTIL_FD_IS_VALID (tmrfd))
 | 
						|
    grub_util_fd_write (tmrfd, buf, grub_strlen (buf));
 | 
						|
#endif
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
static void
 | 
						|
checksum (void)
 | 
						|
{
 | 
						|
  void *ptr;
 | 
						|
  grub_uint32_t crc = 0;
 | 
						|
 | 
						|
  ptr = grub_video_capture_get_framebuffer ();
 | 
						|
 | 
						|
  write_time ();
 | 
						|
 | 
						|
#ifdef GRUB_CPU_WORDS_BIGENDIAN
 | 
						|
  switch (capt_mode_info.bytes_per_pixel)
 | 
						|
    {
 | 
						|
    case 1:
 | 
						|
      crc = grub_getcrc32c (0, ptr, capt_mode_info.pitch
 | 
						|
			    * capt_mode_info.height);
 | 
						|
      break;
 | 
						|
    case 2:
 | 
						|
      {
 | 
						|
	unsigned x, y, rowskip;
 | 
						|
	grub_uint8_t *iptr = ptr;
 | 
						|
	crc = 0;
 | 
						|
	rowskip = capt_mode_info.pitch - capt_mode_info.width * 2;
 | 
						|
	for (y = 0; y < capt_mode_info.height; y++)
 | 
						|
	  {
 | 
						|
	    for (x = 0; x < capt_mode_info.width; x++)
 | 
						|
	      {
 | 
						|
		crc = grub_getcrc32c (crc, iptr + 1, 1);
 | 
						|
		crc = grub_getcrc32c (crc, iptr, 1);
 | 
						|
		iptr += 2;
 | 
						|
	      }
 | 
						|
	    crc = grub_getcrc32c (crc, iptr, rowskip);
 | 
						|
	    iptr += rowskip;
 | 
						|
	  }
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    case 3:
 | 
						|
      {
 | 
						|
	unsigned x, y, rowskip;
 | 
						|
	grub_uint8_t *iptr = ptr;
 | 
						|
	crc = 0;
 | 
						|
	rowskip = capt_mode_info.pitch - capt_mode_info.width * 3;
 | 
						|
	for (y = 0; y < capt_mode_info.height; y++)
 | 
						|
	  {
 | 
						|
	    for (x = 0; x < capt_mode_info.width; x++)
 | 
						|
	      {
 | 
						|
		crc = grub_getcrc32c (crc, iptr + 2, 1);
 | 
						|
		crc = grub_getcrc32c (crc, iptr + 1, 1);
 | 
						|
		crc = grub_getcrc32c (crc, iptr, 1);
 | 
						|
		iptr += 3;
 | 
						|
	      }
 | 
						|
	    crc = grub_getcrc32c (crc, iptr, rowskip);
 | 
						|
	    iptr += rowskip;
 | 
						|
	  }
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    case 4:
 | 
						|
      {
 | 
						|
	unsigned x, y, rowskip;
 | 
						|
	grub_uint8_t *iptr = ptr;
 | 
						|
	crc = 0;
 | 
						|
	rowskip = capt_mode_info.pitch - capt_mode_info.width * 4;
 | 
						|
	for (y = 0; y < capt_mode_info.height; y++)
 | 
						|
	  {
 | 
						|
	    for (x = 0; x < capt_mode_info.width; x++)
 | 
						|
	      {
 | 
						|
		crc = grub_getcrc32c (crc, iptr + 3, 1);
 | 
						|
		crc = grub_getcrc32c (crc, iptr + 2, 1);
 | 
						|
		crc = grub_getcrc32c (crc, iptr + 1, 1);
 | 
						|
		crc = grub_getcrc32c (crc, iptr, 1);
 | 
						|
		iptr += 4;
 | 
						|
	      }
 | 
						|
	    crc = grub_getcrc32c (crc, iptr, rowskip);
 | 
						|
	    iptr += rowskip;
 | 
						|
	  }
 | 
						|
	break;
 | 
						|
      }
 | 
						|
    }
 | 
						|
#else
 | 
						|
  crc = grub_getcrc32c (0, ptr, capt_mode_info.pitch * capt_mode_info.height);
 | 
						|
#endif
 | 
						|
 | 
						|
#if defined (GENERATE_MODE) && defined (GRUB_MACHINE_EMU)
 | 
						|
  if (GRUB_UTIL_FD_IS_VALID (genfd))
 | 
						|
    {
 | 
						|
      char buf[20];
 | 
						|
      grub_snprintf (buf, sizeof (buf), "0x%x, ", crc);
 | 
						|
      grub_util_fd_write (genfd, buf, grub_strlen (buf));
 | 
						|
    }
 | 
						|
#endif
 | 
						|
 | 
						|
  if (!checksums || ctr >= nchk)
 | 
						|
    {
 | 
						|
      grub_test_assert (0, "Unexpected checksum %s_%dx%dx%s:%d: 0x%x",
 | 
						|
			basename, 			
 | 
						|
			capt_mode_info.width,
 | 
						|
			capt_mode_info.height, 
 | 
						|
			grub_video_checksum_get_modename (), ctr, crc);
 | 
						|
    }
 | 
						|
  else if (crc != checksums[ctr])
 | 
						|
    {
 | 
						|
      grub_test_assert (0, "Checksum %s_%dx%dx%s:%d failed: 0x%x vs 0x%x",
 | 
						|
			basename,
 | 
						|
			capt_mode_info.width,
 | 
						|
			capt_mode_info.height,
 | 
						|
			grub_video_checksum_get_modename (),
 | 
						|
			ctr, crc, checksums[ctr]);
 | 
						|
    }
 | 
						|
#if !(defined (SAVE_ALL_IMAGES) && defined (GRUB_MACHINE_EMU))
 | 
						|
  else
 | 
						|
    {
 | 
						|
      write_time ();
 | 
						|
      ctr++;
 | 
						|
      return;
 | 
						|
    }
 | 
						|
#endif
 | 
						|
#ifdef GRUB_MACHINE_EMU
 | 
						|
  char *name = grub_xasprintf ("%s_%dx%dx%s_%d.bmp", basename, 
 | 
						|
			       capt_mode_info.width,
 | 
						|
			       capt_mode_info.height,
 | 
						|
			       grub_video_checksum_get_modename (),
 | 
						|
			       ctr);
 | 
						|
  grub_video_capture_write_bmp (name, ptr, &capt_mode_info);
 | 
						|
  grub_free (name);
 | 
						|
#endif
 | 
						|
 | 
						|
  write_time ();
 | 
						|
 | 
						|
  ctr++;
 | 
						|
}
 | 
						|
 | 
						|
struct checksum_desc
 | 
						|
{
 | 
						|
  const char *name;
 | 
						|
  unsigned width;
 | 
						|
  unsigned height;
 | 
						|
  unsigned mode_type;
 | 
						|
  unsigned number_of_colors;
 | 
						|
  unsigned bpp;
 | 
						|
  unsigned bytes_per_pixel;
 | 
						|
  unsigned red_field_pos;
 | 
						|
  unsigned red_mask_size;
 | 
						|
  unsigned green_field_pos;
 | 
						|
  unsigned green_mask_size;
 | 
						|
  unsigned blue_field_pos;
 | 
						|
  unsigned blue_mask_size;
 | 
						|
  unsigned reserved_field_pos;
 | 
						|
  unsigned reserved_mask_size;
 | 
						|
  const grub_uint32_t *checksums;
 | 
						|
  int nchk;
 | 
						|
};
 | 
						|
 | 
						|
const struct checksum_desc checksum_table[] = {
 | 
						|
#include "checksums.h"
 | 
						|
};
 | 
						|
 | 
						|
void
 | 
						|
grub_video_checksum (const char *basename_in)
 | 
						|
{
 | 
						|
  unsigned i;
 | 
						|
 | 
						|
  grub_video_get_info (&capt_mode_info);
 | 
						|
 | 
						|
#if defined (GENERATE_MODE) && defined (GRUB_MACHINE_EMU)
 | 
						|
  if (!GRUB_UTIL_FD_IS_VALID (genfd))
 | 
						|
    genfd = grub_util_fd_open ("checksums.h", GRUB_UTIL_FD_O_WRONLY
 | 
						|
			       | GRUB_UTIL_FD_O_CREATTRUNC);
 | 
						|
  if (GRUB_UTIL_FD_IS_VALID (genfd))
 | 
						|
    {
 | 
						|
      char buf[400];
 | 
						|
 | 
						|
      grub_snprintf (buf, sizeof (buf), "\", %d, %d, 0x%x, %d, %d, %d, %d, %d, %d, %d, %d, %d, %d, %d /* %dx%dx%s */, (grub_uint32_t []) { ",
 | 
						|
		     capt_mode_info.width,
 | 
						|
		     capt_mode_info.height,
 | 
						|
		     capt_mode_info.mode_type,
 | 
						|
		     capt_mode_info.number_of_colors,
 | 
						|
		     capt_mode_info.bpp,
 | 
						|
		     capt_mode_info.bytes_per_pixel,
 | 
						|
		     capt_mode_info.red_field_pos,
 | 
						|
		     capt_mode_info.red_mask_size,
 | 
						|
		     capt_mode_info.green_field_pos,
 | 
						|
		     capt_mode_info.green_mask_size,
 | 
						|
		     capt_mode_info.blue_field_pos,
 | 
						|
		     capt_mode_info.blue_mask_size,
 | 
						|
		     capt_mode_info.reserved_field_pos,
 | 
						|
		     capt_mode_info.reserved_mask_size,
 | 
						|
		     capt_mode_info.width,
 | 
						|
		     capt_mode_info.height,
 | 
						|
		     grub_video_checksum_get_modename ());
 | 
						|
 | 
						|
      grub_util_fd_write (genfd, "  { \"", 5);
 | 
						|
      grub_util_fd_write (genfd, basename_in, grub_strlen (basename_in));
 | 
						|
      grub_util_fd_write (genfd, buf, grub_strlen (buf));
 | 
						|
    }
 | 
						|
#endif
 | 
						|
 | 
						|
  basename = grub_strdup (basename_in);
 | 
						|
  nchk = 0;
 | 
						|
  checksums = 0;
 | 
						|
  /* FIXME: optimize this.  */
 | 
						|
  for (i = 0; i < ARRAY_SIZE (checksum_table); i++)
 | 
						|
    if (grub_strcmp (checksum_table[i].name, basename_in) == 0
 | 
						|
	&& capt_mode_info.width == checksum_table[i].width
 | 
						|
	&& capt_mode_info.height == checksum_table[i].height
 | 
						|
	&& capt_mode_info.mode_type == checksum_table[i].mode_type
 | 
						|
	&& capt_mode_info.number_of_colors == checksum_table[i].number_of_colors
 | 
						|
	&& capt_mode_info.bpp == checksum_table[i].bpp
 | 
						|
	&& capt_mode_info.bytes_per_pixel == checksum_table[i].bytes_per_pixel
 | 
						|
	&& capt_mode_info.red_field_pos == checksum_table[i].red_field_pos
 | 
						|
	&& capt_mode_info.red_mask_size == checksum_table[i].red_mask_size
 | 
						|
	&& capt_mode_info.green_field_pos == checksum_table[i].green_field_pos
 | 
						|
	&& capt_mode_info.green_mask_size == checksum_table[i].green_mask_size
 | 
						|
	&& capt_mode_info.blue_field_pos == checksum_table[i].blue_field_pos
 | 
						|
	&& capt_mode_info.blue_mask_size == checksum_table[i].blue_mask_size
 | 
						|
	&& capt_mode_info.reserved_field_pos == checksum_table[i].reserved_field_pos
 | 
						|
	&& capt_mode_info.reserved_mask_size == checksum_table[i].reserved_mask_size)
 | 
						|
      {
 | 
						|
	nchk = checksum_table[i].nchk;
 | 
						|
	checksums = checksum_table[i].checksums;
 | 
						|
	break;
 | 
						|
      }
 | 
						|
 | 
						|
  ctr = 0;
 | 
						|
  grub_video_capture_refresh_cb = checksum;
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
grub_video_checksum_end (void)
 | 
						|
{
 | 
						|
#if defined (GENERATE_MODE) && defined (GRUB_MACHINE_EMU)
 | 
						|
  if (GRUB_UTIL_FD_IS_VALID (genfd))
 | 
						|
    {
 | 
						|
      char buf[40];
 | 
						|
      grub_snprintf (buf, sizeof (buf), "}, %d },\n", ctr);
 | 
						|
      grub_util_fd_write (genfd, buf, grub_strlen (buf));
 | 
						|
    }
 | 
						|
#endif
 | 
						|
  grub_test_assert (ctr == nchk, "Not enough checksums %s_%dx%dx%s: %d vs %d",
 | 
						|
		    basename,
 | 
						|
		    capt_mode_info.width,
 | 
						|
		    capt_mode_info.height,
 | 
						|
		    grub_video_checksum_get_modename (),
 | 
						|
		    ctr, nchk);
 | 
						|
  grub_free (basename);
 | 
						|
  basename = 0;
 | 
						|
  nchk = 0;
 | 
						|
  checksums = 0;
 | 
						|
  ctr = 0;
 | 
						|
  grub_video_capture_refresh_cb = 0;
 | 
						|
}
 | 
						|
 | 
						|
static struct grub_term_output *saved_outputs;
 | 
						|
static struct grub_term_output *saved_gfxnext;
 | 
						|
static struct grub_term_output *gfxterm;
 | 
						|
static int use_gfxterm = 0;
 | 
						|
 | 
						|
int
 | 
						|
grub_test_use_gfxterm (void)
 | 
						|
{
 | 
						|
  FOR_ACTIVE_TERM_OUTPUTS (gfxterm)
 | 
						|
    if (grub_strcmp (gfxterm->name, "gfxterm") == 0)
 | 
						|
      break;
 | 
						|
  if (!gfxterm)
 | 
						|
    FOR_DISABLED_TERM_OUTPUTS (gfxterm)
 | 
						|
      if (grub_strcmp (gfxterm->name, "gfxterm") == 0)
 | 
						|
	break;
 | 
						|
 | 
						|
  if (!gfxterm)
 | 
						|
    {
 | 
						|
      grub_test_assert (0, "terminal `%s' isn't found", "gfxterm");
 | 
						|
      return 1;
 | 
						|
    }
 | 
						|
 | 
						|
  if (gfxterm->init (gfxterm))
 | 
						|
    { 
 | 
						|
      grub_test_assert (0, "terminal `%s' failed: %s", "gfxterm", grub_errmsg);
 | 
						|
      return 1;
 | 
						|
    }
 | 
						|
 | 
						|
  saved_outputs = grub_term_outputs;
 | 
						|
  saved_gfxnext = gfxterm->next;
 | 
						|
  grub_term_outputs = gfxterm;
 | 
						|
  gfxterm->next = 0;
 | 
						|
  use_gfxterm = 1;
 | 
						|
 | 
						|
  return 0;
 | 
						|
}
 | 
						|
 | 
						|
void
 | 
						|
grub_test_use_gfxterm_end (void)
 | 
						|
{
 | 
						|
  if (!use_gfxterm)
 | 
						|
    return;
 | 
						|
  use_gfxterm = 0;
 | 
						|
  gfxterm->fini (gfxterm);
 | 
						|
  gfxterm->next = saved_gfxnext;
 | 
						|
  grub_term_outputs = saved_outputs;
 | 
						|
  saved_outputs = 0;
 | 
						|
  saved_gfxnext = 0;
 | 
						|
}
 |