font preload

This commit is contained in:
phcoder 2009-10-24 12:44:42 +02:00
parent 3c842eea9f
commit a9b7a540bd
5 changed files with 114 additions and 27 deletions

View file

@ -17,7 +17,6 @@
* along with GRUB. If not, see <http://www.gnu.org/licenses/>. * along with GRUB. If not, see <http://www.gnu.org/licenses/>.
*/ */
#include <grub/bufio.h>
#include <grub/dl.h> #include <grub/dl.h>
#include <grub/file.h> #include <grub/file.h>
#include <grub/font.h> #include <grub/font.h>
@ -374,25 +373,12 @@ read_section_as_short (struct font_file_section *section, grub_int16_t *value)
/* Load a font and add it to the beginning of the global font list. /* Load a font and add it to the beginning of the global font list.
Returns 0 upon success, nonzero upon failure. */ Returns 0 upon success, nonzero upon failure. */
int int
grub_font_load (const char *filename) grub_font_load (grub_file_t file)
{ {
grub_file_t file = 0;
struct font_file_section section; struct font_file_section section;
char magic[4]; char magic[4];
grub_font_t font = 0; grub_font_t font = 0;
#if FONT_DEBUG >= 1
grub_printf("add_font(%s)\n", filename);
#endif
file = grub_buffile_open (filename, 1024);
if (!file)
goto fail;
#if FONT_DEBUG >= 3
grub_printf("file opened\n");
#endif
/* Read the FILE section. It indicates the file format. */ /* Read the FILE section. It indicates the file format. */
if (open_section (file, &section) != 0) if (open_section (file, &section) != 0)
goto fail; goto fail;

View file

@ -17,10 +17,13 @@
* along with GRUB. If not, see <http://www.gnu.org/licenses/>. * along with GRUB. If not, see <http://www.gnu.org/licenses/>.
*/ */
#include <grub/bufio.h>
#include <grub/font.h> #include <grub/font.h>
#include <grub/dl.h> #include <grub/dl.h>
#include <grub/misc.h> #include <grub/misc.h>
#include <grub/command.h> #include <grub/command.h>
#include <grub/kernel.h>
#include <grub/mm.h>
static grub_err_t static grub_err_t
loadfont_command (grub_command_t cmd __attribute__ ((unused)), loadfont_command (grub_command_t cmd __attribute__ ((unused)),
@ -31,8 +34,16 @@ loadfont_command (grub_command_t cmd __attribute__ ((unused)),
return grub_error (GRUB_ERR_BAD_ARGUMENT, "no font specified"); return grub_error (GRUB_ERR_BAD_ARGUMENT, "no font specified");
while (argc--) while (argc--)
if (grub_font_load (*args++) != 0) {
grub_file_t file = 0;
file = grub_buffile_open (*args++, 1024);
if (!file)
return grub_errno;
if (grub_font_load (file) != 0)
return GRUB_ERR_BAD_FONT; return GRUB_ERR_BAD_FONT;
}
return GRUB_ERR_NONE; return GRUB_ERR_NONE;
} }
@ -54,12 +65,67 @@ lsfonts_command (grub_command_t cmd __attribute__ ((unused)),
return GRUB_ERR_NONE; return GRUB_ERR_NONE;
} }
static grub_ssize_t
pseudo_file_read (struct grub_file *file, char *buf, grub_size_t len)
{
grub_memcpy (buf, (char *) file->data + file->offset, len);
return len;
}
static grub_err_t
pseudo_file_close (struct grub_file *file)
{
grub_free (file->data);
file->data = 0;
return GRUB_ERR_NONE;
}
/* Filesystem descriptor. */
static struct grub_fs pseudo_fs =
{
.name = "Font Loader",
.read = pseudo_file_read,
.close = pseudo_file_close
};
static int
load_font_module (struct grub_module_header *header)
{
grub_file_t file;
if (header->type != OBJ_TYPE_FONT)
return 0;
file = grub_malloc (sizeof (*file));
file->read_hook = 0;
file->offset = 0;
file->size = header->size - sizeof (struct grub_module_header);
file->data = grub_malloc (header->size - sizeof (struct grub_module_header));
if (!file->data)
return 0;
grub_memcpy (file->data, (char *) header + sizeof (struct grub_module_header),
file->size);
file->device = 0;
file->fs = &pseudo_fs;
grub_font_load (file);
return 0;
}
static grub_command_t cmd_loadfont, cmd_lsfonts; static grub_command_t cmd_loadfont, cmd_lsfonts;
GRUB_MOD_INIT(font_manager) GRUB_MOD_INIT(font_manager)
{ {
grub_font_loader_init (); grub_font_loader_init ();
grub_module_iterate (load_font_module);
cmd_loadfont = cmd_loadfont =
grub_register_command ("loadfont", loadfont_command, grub_register_command ("loadfont", loadfont_command,
"loadfont FILE...", "loadfont FILE...",

View file

@ -21,6 +21,7 @@
#include <grub/types.h> #include <grub/types.h>
#include <grub/video.h> #include <grub/video.h>
#include <grub/file.h>
/* Forward declaration of opaque structure grub_font. /* Forward declaration of opaque structure grub_font.
Users only pass struct grub_font pointers to the font module functions, Users only pass struct grub_font pointers to the font module functions,
@ -74,7 +75,7 @@ void grub_font_loader_init (void);
/* Load a font and add it to the beginning of the global font list. /* Load a font and add it to the beginning of the global font list.
Returns: 0 upon success; nonzero upon failure. */ Returns: 0 upon success; nonzero upon failure. */
int grub_font_load (const char *filename); int grub_font_load (grub_file_t file);
/* Get the font that has the specified name. Font names are in the form /* Get the font that has the specified name. Font names are in the form
"Family Name Bold Italic 14", where Bold and Italic are optional. "Family Name Bold Italic 14", where Bold and Italic are optional.

View file

@ -26,7 +26,8 @@ enum
{ {
OBJ_TYPE_ELF, OBJ_TYPE_ELF,
OBJ_TYPE_MEMDISK, OBJ_TYPE_MEMDISK,
OBJ_TYPE_CONFIG OBJ_TYPE_CONFIG,
OBJ_TYPE_FONT
}; };
/* The module header. */ /* The module header. */

View file

@ -93,7 +93,7 @@ compress_kernel (char *kernel_img, size_t kernel_size,
static void static void
generate_image (const char *dir, char *prefix, FILE *out, char *mods[], generate_image (const char *dir, char *prefix, FILE *out, char *mods[],
char *memdisk_path, char *config_path, char *memdisk_path, char *font_path, char *config_path,
#ifdef GRUB_PLATFORM_IMAGE_DEFAULT #ifdef GRUB_PLATFORM_IMAGE_DEFAULT
grub_platform_image_format_t format grub_platform_image_format_t format
#else #else
@ -104,7 +104,7 @@ generate_image (const char *dir, char *prefix, FILE *out, char *mods[],
{ {
char *kernel_img, *core_img; char *kernel_img, *core_img;
size_t kernel_size, total_module_size, core_size; size_t kernel_size, total_module_size, core_size;
size_t memdisk_size = 0, config_size = 0; size_t memdisk_size = 0, font_size = 0, config_size = 0;
char *kernel_path; char *kernel_path;
size_t offset; size_t offset;
struct grub_util_path_list *path_list, *p, *next; struct grub_util_path_list *path_list, *p, *next;
@ -124,6 +124,12 @@ generate_image (const char *dir, char *prefix, FILE *out, char *mods[],
total_module_size += memdisk_size + sizeof (struct grub_module_header); total_module_size += memdisk_size + sizeof (struct grub_module_header);
} }
if (font_path)
{
font_size = ALIGN_UP(grub_util_get_image_size (font_path), 4);
total_module_size += font_size + sizeof (struct grub_module_header);
}
if (config_path) if (config_path)
{ {
config_size = grub_util_get_image_size (config_path) + 1; config_size = grub_util_get_image_size (config_path) + 1;
@ -183,6 +189,20 @@ generate_image (const char *dir, char *prefix, FILE *out, char *mods[],
offset += memdisk_size; offset += memdisk_size;
} }
if (font_path)
{
struct grub_module_header *header;
header = (struct grub_module_header *) (kernel_img + offset);
memset (header, 0, sizeof (struct grub_module_header));
header->type = OBJ_TYPE_FONT;
header->size = grub_host_to_target32 (font_size + sizeof (*header));
offset += sizeof (*header);
grub_util_load_image (font_path, kernel_img + offset);
offset += font_size;
}
if (config_path) if (config_path)
{ {
struct grub_module_header *header; struct grub_module_header *header;
@ -339,7 +359,10 @@ generate_image (const char *dir, char *prefix, FILE *out, char *mods[],
phdr->p_flags = grub_host_to_target32 (PF_R | PF_W | PF_X); phdr->p_flags = grub_host_to_target32 (PF_R | PF_W | PF_X);
target_addr = ALIGN_UP (GRUB_KERNEL_MACHINE_LINK_ADDR target_addr = ALIGN_UP (GRUB_KERNEL_MACHINE_LINK_ADDR
+ kernel_size + total_module_size, 32); + kernel_size + total_module_size
+ 0x100000
// + BSS_SIZE
, 32);
ehdr->e_entry = grub_host_to_target32 (target_addr); ehdr->e_entry = grub_host_to_target32 (target_addr);
phdr->p_vaddr = grub_host_to_target32 (target_addr); phdr->p_vaddr = grub_host_to_target32 (target_addr);
phdr->p_paddr = grub_host_to_target32 (target_addr); phdr->p_paddr = grub_host_to_target32 (target_addr);
@ -376,10 +399,11 @@ static struct option options[] =
{"directory", required_argument, 0, 'd'}, {"directory", required_argument, 0, 'd'},
{"prefix", required_argument, 0, 'p'}, {"prefix", required_argument, 0, 'p'},
{"memdisk", required_argument, 0, 'm'}, {"memdisk", required_argument, 0, 'm'},
{"font", required_argument, 0, 'f'},
{"config", required_argument, 0, 'c'}, {"config", required_argument, 0, 'c'},
{"output", required_argument, 0, 'o'}, {"output", required_argument, 0, 'o'},
#ifdef GRUB_PLATFORM_IMAGE_DEFAULT #ifdef GRUB_PLATFORM_IMAGE_DEFAULT
{"format", required_argument, 0, 'f'}, {"format", required_argument, 0, 'O'},
#endif #endif
{"help", no_argument, 0, 'h'}, {"help", no_argument, 0, 'h'},
{"version", no_argument, 0, 'V'}, {"version", no_argument, 0, 'V'},
@ -401,11 +425,12 @@ Make a bootable image of GRUB.\n\
-d, --directory=DIR use images and modules under DIR [default=%s]\n\ -d, --directory=DIR use images and modules under DIR [default=%s]\n\
-p, --prefix=DIR set grub_prefix directory [default=%s]\n\ -p, --prefix=DIR set grub_prefix directory [default=%s]\n\
-m, --memdisk=FILE embed FILE as a memdisk image\n\ -m, --memdisk=FILE embed FILE as a memdisk image\n\
-f, --font=FILE embed FILE as a boot font\n\
-c, --config=FILE embed FILE as boot config\n\ -c, --config=FILE embed FILE as boot config\n\
-o, --output=FILE output a generated image to FILE [default=stdout]\n" -o, --output=FILE output a generated image to FILE [default=stdout]\n"
#ifdef GRUB_PLATFORM_IMAGE_DEFAULT #ifdef GRUB_PLATFORM_IMAGE_DEFAULT
"\ "\
-f, --format=FORMAT generate an image in format [default=" -O, --format=FORMAT generate an image in format [default="
GRUB_PLATFORM_IMAGE_DEFAULT_FORMAT "]\n \ GRUB_PLATFORM_IMAGE_DEFAULT_FORMAT "]\n \
available formats: " available formats: "
GRUB_PLATFORM_IMAGE_FORMATS "\n" GRUB_PLATFORM_IMAGE_FORMATS "\n"
@ -428,6 +453,7 @@ main (int argc, char *argv[])
char *dir = NULL; char *dir = NULL;
char *prefix = NULL; char *prefix = NULL;
char *memdisk = NULL; char *memdisk = NULL;
char *font = NULL;
char *config = NULL; char *config = NULL;
FILE *fp = stdout; FILE *fp = stdout;
#ifdef GRUB_PLATFORM_IMAGE_DEFAULT #ifdef GRUB_PLATFORM_IMAGE_DEFAULT
@ -438,7 +464,7 @@ main (int argc, char *argv[])
while (1) while (1)
{ {
int c = getopt_long (argc, argv, "d:p:m:c:o:f:hVv", options, 0); int c = getopt_long (argc, argv, "d:p:m:c:o:O:f:hVv", options, 0);
if (c == -1) if (c == -1)
break; break;
@ -453,7 +479,7 @@ main (int argc, char *argv[])
break; break;
#ifdef GRUB_PLATFORM_IMAGE_DEFAULT #ifdef GRUB_PLATFORM_IMAGE_DEFAULT
case 'f': case 'O':
#ifdef GRUB_PLATFORM_IMAGE_RAW #ifdef GRUB_PLATFORM_IMAGE_RAW
if (strcmp (optarg, "raw") == 0) if (strcmp (optarg, "raw") == 0)
format = GRUB_PLATFORM_IMAGE_RAW; format = GRUB_PLATFORM_IMAGE_RAW;
@ -487,6 +513,13 @@ main (int argc, char *argv[])
prefix = xstrdup ("(memdisk)/boot/grub"); prefix = xstrdup ("(memdisk)/boot/grub");
break; break;
case 'f':
if (font)
free (font);
font = xstrdup (optarg);
break;
case 'c': case 'c':
if (config) if (config)
free (config); free (config);
@ -528,7 +561,7 @@ main (int argc, char *argv[])
} }
generate_image (dir ? : GRUB_LIBDIR, prefix ? : DEFAULT_DIRECTORY, fp, generate_image (dir ? : GRUB_LIBDIR, prefix ? : DEFAULT_DIRECTORY, fp,
argv + optind, memdisk, config, argv + optind, memdisk, font, config,
#ifdef GRUB_PLATFORM_IMAGE_DEFAULT #ifdef GRUB_PLATFORM_IMAGE_DEFAULT
format format
#else #else