Compare commits

...

13 Commits

Author SHA1 Message Date
Vladimir Serbinenko
8e2fb1e3ce More efficient retrieval of file size 2013-10-27 17:24:35 +01:00
Vladimir Serbinenko
442b86de32 Move grub_disk_write out of kernel into disk.mod. 2013-10-27 15:44:55 +01:00
Vladimir Serbinenko
04dea7e6c2 * grub-core/kern/misc.c (grub_vsnprintf_real): Unify int and wchar
handling.
2013-10-27 14:47:04 +01:00
Vladimir Serbinenko
a8f15bceea * grub-core/kern/misc.c (grub_abort): Make static 2013-10-27 14:13:39 +01:00
Vladimir Serbinenko
a60dae7e4e * grub-core/kern/misc.c (grub_vsnprintf_real): Don't attempt to
transform invalid unicode codepoints.
2013-10-27 13:34:46 +01:00
Vladimir Serbinenko
891b713be3 * grub-core/kern/misc.c (grub_vsnprintf_real): Remove needless explicit
\0 checking.
2013-10-27 13:20:50 +01:00
Vladimir Serbinenko
cf880639f6 Revert " * util/grub-mkstandalone.in: Remove needless copying since we already"
The copying in question was needed.

This reverts commit 8154884dd4.
2013-10-27 12:22:52 +01:00
Vladimir Serbinenko
03dcac7f76 * grub-core/lib/legacy_parse.c: Add support for "nd" disk. 2013-10-27 02:50:31 +02:00
Vladimir Serbinenko
c81acb7ff3 Consolidate cpuid code. 2013-10-27 00:02:01 +02:00
Vladimir Serbinenko
c1bee64676 Move cpuid code to cpuid.h and TSC code to tsc.c. 2013-10-26 23:39:10 +02:00
Grégoire Sutre
f37bf9c778 * util/grub.d/00_header.in: Don't use LANG if it's not set. 2013-10-26 20:11:55 +02:00
Grégoire Sutre
4021132be2 Missing Changelog entry 2013-10-26 20:06:24 +02:00
Grégoire Sutre
67811a6fd4 * util/grub-mkconfig.in: Replace $0 with $self.
* util/grub-reboot.in: Likewise.
	* util/grub-set-default.in: Likewise.
2013-10-26 20:05:29 +02:00
54 changed files with 523 additions and 501 deletions

View File

@@ -1,3 +1,48 @@
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
Move grub_disk_write out of kernel into disk.mod.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Unify int and wchar
handling.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_abort): Make static
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Don't attempt to
transform invalid unicode codepoints.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/kern/misc.c (grub_vsnprintf_real): Remove needless explicit
\0 checking.
2013-10-27 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/lib/legacy_parse.c: Add support for "nd" disk.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
Consolidate cpuid code.
2013-10-26 Vladimir Serbinenko <phcoder@gmail.com>
Move cpuid code to cpuid.h and TSC code to tsc.c.
2013-10-26 Grégoire Sutre <gregoire.sutre@gmail.com>
* util/grub.d/00_header.in: Don't use LANG if it's not set.
2013-10-26 Grégoire Sutre <gregoire.sutre@gmail.com>
* util/grub-mkconfig.in: Replace $0 with $self.
* util/grub-reboot.in: Likewise.
* util/grub-set-default.in: Likewise.
2013-10-26 BVK Chaitanya <bvk.groups@gmail.com>
* docs/osdetect.cfg: New file.
@@ -556,11 +601,6 @@
currently used so this doesn't really have any effect.
Reported by: Douglas Ray <dougray>
2013-10-17 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkstandalone.in: Remove needless copying since we already
pass the files to tar.
2013-10-17 Vladimir Serbinenko <phcoder@gmail.com>
* autogen.sh: Don't set LC_CTYPE as it doesn't create problem for

View File

@@ -9,6 +9,7 @@ library = {
common = grub-core/kern/command.c;
common = grub-core/kern/device.c;
common = grub-core/kern/disk.c;
common = grub-core/lib/disk.c;
common = util/getroot.c;
common = grub-core/osdep/unix/getroot.c;
common = grub-core/osdep/getroot.c;

View File

@@ -455,6 +455,11 @@ image = {
enable = mips_loongson;
};
module = {
name = disk;
common = lib/disk.c;
};
module = {
name = trig;
common_nodist = trigtables.c;

View File

@@ -29,11 +29,6 @@
GRUB_MOD_LICENSE ("GPLv3+");
#define cpuid(num,a,b,c,d) \
asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1" \
: "=a" (a), "=r" (b), "=c" (c), "=d" (d) \
: "0" (num))
static const struct grub_arg_option options[] =
{
/* TRANSLATORS: "(default)" at the end means that this option is used if
@@ -78,18 +73,18 @@ GRUB_MOD_INIT(cpuid)
goto done;
/* Check the highest input value for eax. */
cpuid (0, eax, ebx, ecx, edx);
grub_cpuid (0, eax, ebx, ecx, edx);
/* We only look at the first four characters. */
max_level = eax;
if (max_level == 0)
goto done;
cpuid (0x80000000, eax, ebx, ecx, edx);
grub_cpuid (0x80000000, eax, ebx, ecx, edx);
ext_level = eax;
if (ext_level < 0x80000000)
goto done;
cpuid (0x80000001, eax, ebx, ecx, edx);
grub_cpuid (0x80000001, eax, ebx, ecx, edx);
grub_cpuid_has_longmode = !!(edx & bit_LM);
done:
#endif

View File

@@ -116,35 +116,11 @@ print_files_long (const char *filename, const struct grub_dirhook_info *info,
if (! info->dir)
{
grub_file_t file;
char *pathname;
if (ctx->dirname[grub_strlen (ctx->dirname) - 1] == '/')
pathname = grub_xasprintf ("%s%s", ctx->dirname, filename);
else
pathname = grub_xasprintf ("%s/%s", ctx->dirname, filename);
if (!pathname)
return 1;
/* XXX: For ext2fs symlinks are detected as files while they
should be reported as directories. */
grub_file_filter_disable_compression ();
file = grub_file_open (pathname);
if (! file)
{
grub_errno = 0;
grub_free (pathname);
return 0;
}
if (! ctx->human)
grub_printf ("%-12llu", (unsigned long long) file->size);
grub_printf ("%-12llu", (unsigned long long) info->size);
else
grub_printf ("%-12s", grub_get_human_size (file->size,
GRUB_HUMAN_SIZE_SHORT));
grub_file_close (file);
grub_free (pathname);
grub_printf ("%-12s", grub_get_human_size (info->size,
GRUB_HUMAN_SIZE_SHORT));
}
else
grub_printf ("%-12s", _("DIR"));

View File

@@ -631,10 +631,16 @@ grub_cryptodisk_write (grub_disk_t disk, grub_disk_addr_t sector,
return grub_crypto_gcry_error (gcry_err);
}
err = grub_disk_write (dev->source_disk,
(sector << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) + dev->offset,
0, size << disk->log_sector_size, tmp);
/* Since ->write was called so disk.mod is loaded but be paranoid */
if (grub_disk_write_weak)
err = grub_disk_write_weak (dev->source_disk,
(sector << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS))
+ dev->offset,
0, size << disk->log_sector_size, tmp);
else
err = grub_error (GRUB_ERR_BUG, "disk.mod not loaded");
grub_free (tmp);
return err;
}

View File

@@ -18,42 +18,10 @@
#include <grub/efiemu/efiemu.h>
#include <grub/command.h>
#define cpuid(num,a,b,c,d) \
asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1" \
: "=a" (a), "=r" (b), "=c" (c), "=d" (d) \
: "0" (num))
#define bit_LM (1 << 29)
#include <grub/i386/cpuid.h>
const char *
grub_efiemu_get_default_core_name (void)
{
unsigned int eax, ebx, ecx, edx;
unsigned int max_level;
unsigned int ext_level;
/* See if we can use cpuid. */
asm volatile ("pushfl; pushfl; popl %0; movl %0,%1; xorl %2,%0;"
"pushl %0; popfl; pushfl; popl %0; popfl"
: "=&r" (eax), "=&r" (ebx)
: "i" (0x00200000));
if (((eax ^ ebx) & 0x00200000) == 0)
return "efiemu32.o";
/* Check the highest input value for eax. */
cpuid (0, eax, ebx, ecx, edx);
/* We only look at the first four characters. */
max_level = eax;
if (max_level == 0)
return "efiemu32.o";
cpuid (0x80000000, eax, ebx, ecx, edx);
ext_level = eax;
if (ext_level < 0x80000000)
return "efiemu32.o";
cpuid (0x80000001, eax, ebx, ecx, edx);
return (edx & bit_LM) ? "efiemu64.o" : "efiemu32.o";
return grub_cpuid_has_longmode ? "efiemu64.o" : "efiemu32.o";
}

View File

@@ -565,6 +565,7 @@ grub_affs_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.mtimeset = 1;
info.mtime = aftime2ctime (&node->di.mtime);
info.size = grub_be_to_cpu32 (node->di.size);
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);
}

View File

@@ -155,9 +155,10 @@ grub_archelp_dir (struct grub_archelp_data *data,
{
grub_int32_t mtime;
grub_uint32_t mode;
grub_uint64_t size;
grub_err_t err;
if (arcops->find_file (data, &name, &mtime, &mode))
if (arcops->find_file (data, &name, &mtime, &mode, &size))
goto fail;
if (mode == GRUB_ARCHELP_ATTR_END)
@@ -189,6 +190,7 @@ grub_archelp_dir (struct grub_archelp_data *data,
info.mtime = mtime;
info.mtimeset = 1;
}
info.size = size;
if (hook (n, &info, hook_data))
{
grub_free (name);
@@ -248,8 +250,9 @@ grub_archelp_open (struct grub_archelp_data *data,
{
grub_uint32_t mode;
int restart;
grub_uint64_t size;
if (arcops->find_file (data, &fn, NULL, &mode))
if (arcops->find_file (data, &fn, NULL, &mode, &size))
goto fail;
if (mode == GRUB_ARCHELP_ATTR_END)

View File

@@ -889,6 +889,7 @@ grub_bfs_dir_iter (const char *name, grub_uint64_t value,
info.mtime = grub_bfs_to_cpu64 (ino.mtime) >> 16;
#endif
info.dir = ((grub_bfs_to_cpu32 (ino.mode) & ATTR_TYPE) == ATTR_DIR);
info.size = grub_bfs_to_cpu64 (ino.size);
return ctx->hook (name, &info, ctx->hook_data);
}

View File

@@ -1580,6 +1580,7 @@ grub_btrfs_dir (grub_device_t device, const char *path,
else
{
info.mtime = grub_le_to_cpu64 (inode.mtime.sec);
info.size = grub_le_to_cpu64 (inode.size);
info.mtimeset = 1;
}
c = cdirel->name[grub_le_to_cpu16 (cdirel->n)];

View File

@@ -44,7 +44,8 @@ struct grub_archelp_data
static grub_err_t
grub_cbfs_find_file (struct grub_archelp_data *data, char **name,
grub_int32_t *mtime,
grub_uint32_t *mode)
grub_uint32_t *mode,
grub_uint64_t *size)
{
grub_size_t offset;
for (;;
@@ -71,6 +72,7 @@ grub_cbfs_find_file (struct grub_archelp_data *data, char **name,
return GRUB_ERR_NONE;
}
data->size = grub_be_to_cpu32 (hd.len);
*size = grub_be_to_cpu32 (hd.len);
(void) mtime;
offset = grub_be_to_cpu32 (hd.offset);

View File

@@ -38,7 +38,8 @@ struct grub_archelp_data
static grub_err_t
grub_cpio_find_file (struct grub_archelp_data *data, char **name,
grub_int32_t *mtime, grub_uint32_t *mode)
grub_int32_t *mtime, grub_uint32_t *mode,
grub_uint64_t *size)
{
struct head hd;
grub_size_t namesize;
@@ -86,6 +87,7 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
data->dofs = data->hofs + ALIGN_CPIO (sizeof (hd) + namesize);
data->next_hofs = data->dofs + ALIGN_CPIO (data->size);
*size = data->size;
return GRUB_ERR_NONE;
}

View File

@@ -884,6 +884,8 @@ grub_ext2_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
{
info.mtimeset = 1;
info.mtime = grub_le_to_cpu32 (node->inode.mtime);
info.size = grub_le_to_cpu32 (node->inode.size);
info.size |= ((grub_off_t) grub_le_to_cpu32 (node->inode.size_high)) << 32;
}
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);

View File

@@ -938,6 +938,8 @@ grub_fat_find_dir (grub_disk_t disk, struct grub_fat_data *data,
#endif
data->cur_cluster_num = ~0U;
info.size = data->file_size;
if (call_hook)
hook (ctxt.filename, &info, hook_data);

View File

@@ -1237,6 +1237,7 @@ grub_hfs_dir_hook (struct grub_hfs_record *rec, void *hook_arg)
info.dir = 0;
info.mtimeset = 1;
info.mtime = grub_be_to_cpu32 (frec->mtime) - 2082844800;
info.size = grub_be_to_cpu32 (frec->size);
return ctx->hook (fname, &info, ctx->hook_data);
}

View File

@@ -917,6 +917,7 @@ grub_hfsplus_dir_iter (const char *filename,
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.mtimeset = 1;
info.mtime = node->mtime;
info.size = node->size;
info.case_insensitive = !! (filetype & GRUB_FSHELP_CASE_INSENSITIVE);
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);

View File

@@ -861,7 +861,7 @@ grub_iso9660_dir_iter (const char *filename,
grub_memset (&info, 0, sizeof (info));
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.mtimeset = !!iso9660_to_unixtime2 (&node->dirents[0].mtime, &info.mtime);
info.size = get_node_size (node);
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);
}

View File

@@ -778,6 +778,7 @@ grub_jfs_dir (grub_device_t device, const char *path,
& GRUB_JFS_FILETYPE_MASK) == GRUB_JFS_FILETYPE_DIR;
info.mtimeset = 1;
info.mtime = grub_le_to_cpu32 (inode.mtime.sec);
info.size = grub_le_to_cpu64 (inode.size);
if (hook (diro->name, &info, hook_data))
goto fail;
}

View File

@@ -576,6 +576,7 @@ grub_minix_dir (grub_device_t device, const char *path,
& GRUB_MINIX_IFDIR) == GRUB_MINIX_IFDIR);
info.mtimeset = 1;
info.mtime = grub_minix_to_cpu32 (data->inode.mtime);
info.size = GRUB_MINIX_INODE_SIZE (data);
if (hook (filename, &info, hook_data) ? 1 : 0)
break;

View File

@@ -1066,6 +1066,7 @@ grub_nilfs2_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
{
info.mtimeset = 1;
info.mtime = grub_le_to_cpu64 (node->inode.i_mtime);
info.size = grub_le_to_cpu64 (node->inode.i_size);
}
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);

View File

@@ -981,10 +981,13 @@ grub_ntfs_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
grub_memset (&info, 0, sizeof (info));
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
init_file (node, node->ino);
info.mtimeset = 1;
info.mtime = grub_divmod64 (node->mtime, 10000000, 0)
- 86400ULL * 365 * (1970 - 1601)
- 86400ULL * ((1970 - 1601) / 4) + 86400ULL * ((1970 - 1601) / 100);
info.mtime = node->size;
free_file (node);
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);
}

View File

@@ -1271,6 +1271,7 @@ grub_reiserfs_dir_iter (const char *filename,
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.mtimeset = 1;
info.mtime = node->mtime;
info.size = node->size;
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);
}

View File

@@ -331,6 +331,7 @@ grub_romfs_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
grub_memset (&info, 0, sizeof (info));
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.size = grub_be_to_cpu32 (node->file.size);
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);
}

View File

@@ -671,6 +671,7 @@ grub_sfs_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.mtime = node->mtime + 8 * 365 * 86400 + 86400 * 2;
info.mtimeset = 1;
info.size = node->size;
grub_free (node->cache);
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);

View File

@@ -656,6 +656,15 @@ grub_squash_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
info.mtimeset = 1;
info.mtime = grub_le_to_cpu32 (node->ino.mtime);
switch (node->ino.type)
{
case grub_cpu_to_le16_compile_time (SQUASH_TYPE_LONG_REGULAR):
info.size = grub_le_to_cpu64 (node->ino.long_file.size);
break;
case grub_cpu_to_le16_compile_time (SQUASH_TYPE_REGULAR):
info.size = grub_le_to_cpu32 (node->ino.file.size);
break;
}
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);
}

View File

@@ -72,7 +72,8 @@ struct grub_archelp_data
static grub_err_t
grub_cpio_find_file (struct grub_archelp_data *data, char **name,
grub_int32_t *mtime,
grub_uint32_t *mode)
grub_uint32_t *mode,
grub_uint64_t *size)
{
struct head hd;
int reread = 0, have_longname = 0, have_longlink = 0;
@@ -200,6 +201,7 @@ grub_cpio_find_file (struct grub_archelp_data *data, char **name,
grub_memcpy (data->linkname, hd.linkname, sizeof (hd.linkname));
data->linkname[100] = 0;
}
*size = data->size;
return GRUB_ERR_NONE;
}
return GRUB_ERR_NONE;

View File

@@ -1072,6 +1072,7 @@ grub_udf_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
info.mtimeset = !!grub_datetime2unixtime (&datetime, &info.mtime);
info.mtime -= 60 * tz;
info.size = U64 (node->block.fe.file_size);
}
grub_free (node);
return ctx->hook (filename, &info, ctx->hook_data);

View File

@@ -711,6 +711,8 @@ grub_ufs_dir (grub_device_t device, const char *path,
#endif
info.mtimeset = 1;
info.size = grub_ufs_to_cpu64 (inode.size);
if (hook (filename, &info, hook_data))
{
grub_free (filename);

View File

@@ -732,6 +732,7 @@ grub_xfs_dir_iter (const char *filename, enum grub_fshelp_filetype filetype,
{
info.mtimeset = 1;
info.mtime = grub_be_to_cpu32 (node->inode.mtime.sec);
info.size = grub_be_to_cpu64 (node->inode.size);
}
info.dir = ((filetype & GRUB_FSHELP_TYPE_MASK) == GRUB_FSHELP_DIR);
grub_free (node);

View File

@@ -3999,6 +3999,8 @@ iterate_zap (const char *name, grub_uint64_t val, struct grub_zfs_dir_ctx *ctx)
info.mtimeset = 1;
info.mtime = grub_zfs_to_cpu64 (grub_get_unaligned64 ((char *) sahdrp + hdrsize + SA_MTIME_OFFSET), dn.endian);
info.case_insensitive = ctx->data->subvol.case_insensitive;
info.size = grub_zfs_to_cpu64 (grub_get_unaligned64 ((char *) sahdrp + hdrsize + SA_SIZE_OFFSET), dn.endian);
}
if (dn.dn.dn_bonustype == DMU_OT_ZNODE)
@@ -4006,6 +4008,7 @@ iterate_zap (const char *name, grub_uint64_t val, struct grub_zfs_dir_ctx *ctx)
info.mtimeset = 1;
info.mtime = grub_zfs_to_cpu64 (((znode_phys_t *) DN_BONUS (&dn.dn))->zp_mtime[0],
dn.endian);
info.size = grub_zfs_to_cpu64 (((znode_phys_t *) DN_BONUS (&dn.dn))->zp_size, dn.endian);
}
info.dir = (dn.dn.dn_type == DMU_OT_DIRECTORY_CONTENTS);
grub_dprintf ("zfs", "type=%d, name=%s\n",

View File

@@ -216,7 +216,7 @@ grub_gdb_trap (int trap_no)
grub_backtrace_print_address ((void *) grub_gdb_regs[PC]);
grub_printf ("\n");
grub_backtrace_pointer ((void *) grub_gdb_regs[EBP]);
grub_abort ();
grub_fatal ("Unhandled exception");
}
sig_no = grub_gdb_trap2sig (trap_no);

View File

@@ -31,18 +31,7 @@
/* The last time the disk was used. */
static grub_uint64_t grub_last_time = 0;
/* Disk cache. */
struct grub_disk_cache
{
enum grub_disk_dev_id dev_id;
unsigned long disk_id;
grub_disk_addr_t sector;
char *data;
int lock;
};
static struct grub_disk_cache grub_disk_cache_table[GRUB_DISK_CACHE_NUM];
struct grub_disk_cache grub_disk_cache_table[GRUB_DISK_CACHE_NUM];
void (*grub_disk_firmware_fini) (void);
int grub_disk_firmware_is_tainted;
@@ -59,35 +48,12 @@ grub_disk_cache_get_performance (unsigned long *hits, unsigned long *misses)
}
#endif
static unsigned
grub_disk_cache_get_index (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
return ((dev_id * 524287UL + disk_id * 2606459UL
+ ((unsigned) (sector >> GRUB_DISK_CACHE_BITS)))
% GRUB_DISK_CACHE_NUM);
}
static void
grub_disk_cache_invalidate (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
unsigned cache_index;
struct grub_disk_cache *cache;
sector &= ~(GRUB_DISK_CACHE_SIZE - 1);
cache_index = grub_disk_cache_get_index (dev_id, disk_id, sector);
cache = grub_disk_cache_table + cache_index;
if (cache->dev_id == dev_id && cache->disk_id == disk_id
&& cache->sector == sector && cache->data)
{
cache->lock = 1;
grub_free (cache->data);
cache->data = 0;
cache->lock = 0;
}
}
grub_err_t (*grub_disk_write_weak) (grub_disk_t disk,
grub_disk_addr_t sector,
grub_off_t offset,
grub_size_t size,
const void *buf);
#include "disk_common.c"
void
grub_disk_cache_invalidate_all (void)
@@ -341,53 +307,6 @@ grub_disk_close (grub_disk_t disk)
grub_free (disk);
}
/* This function performs three tasks:
- Make sectors disk relative from partition relative.
- Normalize offset to be less than the sector size.
- Verify that the range is inside the partition. */
static grub_err_t
grub_disk_adjust_range (grub_disk_t disk, grub_disk_addr_t *sector,
grub_off_t *offset, grub_size_t size)
{
grub_partition_t part;
*sector += *offset >> GRUB_DISK_SECTOR_BITS;
*offset &= GRUB_DISK_SECTOR_SIZE - 1;
for (part = disk->partition; part; part = part->parent)
{
grub_disk_addr_t start;
grub_uint64_t len;
start = part->start;
len = part->len;
if (*sector >= len
|| len - *sector < ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of partition"));
*sector += start;
}
if (disk->total_sectors != GRUB_DISK_SIZE_UNKNOWN
&& ((disk->total_sectors << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS)) <= *sector
|| ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS) > (disk->total_sectors
<< (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - *sector))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of disk `%s'"), disk->name);
return GRUB_ERR_NONE;
}
static inline grub_disk_addr_t
transform_sector (grub_disk_t disk, grub_disk_addr_t sector)
{
return sector >> (disk->log_sector_size - GRUB_DISK_SECTOR_BITS);
}
/* Small read (less than cache size and not pass across cache unit boundaries).
sector is already adjusted and is divisible by cache unit size.
*/
@@ -613,98 +532,6 @@ grub_disk_read (grub_disk_t disk, grub_disk_addr_t sector,
return grub_errno;
}
grub_err_t
grub_disk_write (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, const void *buf)
{
unsigned real_offset;
grub_disk_addr_t aligned_sector;
grub_dprintf ("disk", "Writing `%s'...\n", disk->name);
if (grub_disk_adjust_range (disk, &sector, &offset, size) != GRUB_ERR_NONE)
return -1;
aligned_sector = (sector & ~((1 << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - 1));
real_offset = offset + ((sector - aligned_sector) << GRUB_DISK_SECTOR_BITS);
sector = aligned_sector;
while (size)
{
if (real_offset != 0 || (size < (1U << disk->log_sector_size)
&& size != 0))
{
char *tmp_buf;
grub_size_t len;
grub_partition_t part;
tmp_buf = grub_malloc (1 << disk->log_sector_size);
if (!tmp_buf)
return grub_errno;
part = disk->partition;
disk->partition = 0;
if (grub_disk_read (disk, sector,
0, (1 << disk->log_sector_size), tmp_buf)
!= GRUB_ERR_NONE)
{
disk->partition = part;
grub_free (tmp_buf);
goto finish;
}
disk->partition = part;
len = (1 << disk->log_sector_size) - real_offset;
if (len > size)
len = size;
grub_memcpy (tmp_buf + real_offset, buf, len);
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
if ((disk->dev->write) (disk, transform_sector (disk, sector),
1, tmp_buf) != GRUB_ERR_NONE)
{
grub_free (tmp_buf);
goto finish;
}
grub_free (tmp_buf);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
buf = (const char *) buf + len;
size -= len;
real_offset = 0;
}
else
{
grub_size_t len;
grub_size_t n;
len = size & ~((1 << disk->log_sector_size) - 1);
n = size >> disk->log_sector_size;
if ((disk->dev->write) (disk, transform_sector (disk, sector),
n, buf) != GRUB_ERR_NONE)
goto finish;
while (n--)
{
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
}
buf = (const char *) buf + len;
size -= len;
}
}
finish:
return grub_errno;
}
grub_uint64_t
grub_disk_get_size (grub_disk_t disk)
{

View File

@@ -0,0 +1,55 @@
/* This function performs three tasks:
- Make sectors disk relative from partition relative.
- Normalize offset to be less than the sector size.
- Verify that the range is inside the partition. */
static grub_err_t
grub_disk_adjust_range (grub_disk_t disk, grub_disk_addr_t *sector,
grub_off_t *offset, grub_size_t size)
{
grub_partition_t part;
*sector += *offset >> GRUB_DISK_SECTOR_BITS;
*offset &= GRUB_DISK_SECTOR_SIZE - 1;
for (part = disk->partition; part; part = part->parent)
{
grub_disk_addr_t start;
grub_uint64_t len;
start = part->start;
len = part->len;
if (*sector >= len
|| len - *sector < ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of partition"));
*sector += start;
}
if (disk->total_sectors != GRUB_DISK_SIZE_UNKNOWN
&& ((disk->total_sectors << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS)) <= *sector
|| ((*offset + size + GRUB_DISK_SECTOR_SIZE - 1)
>> GRUB_DISK_SECTOR_BITS) > (disk->total_sectors
<< (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - *sector))
return grub_error (GRUB_ERR_OUT_OF_RANGE,
N_("attempt to read or write outside of disk `%s'"), disk->name);
return GRUB_ERR_NONE;
}
static inline grub_disk_addr_t
transform_sector (grub_disk_t disk, grub_disk_addr_t sector)
{
return sector >> (disk->log_sector_size - GRUB_DISK_SECTOR_BITS);
}
static unsigned
grub_disk_cache_get_index (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
return ((dev_id * 524287UL + disk_id * 2606459UL
+ ((unsigned) (sector >> GRUB_DISK_CACHE_BITS)))
% GRUB_DISK_CACHE_NUM);
}

View File

@@ -511,7 +511,7 @@ grub_efi_mm_init (void)
grub_printf ("printing memory map\n");
print_memory_map (memory_map, desc_size,
NEXT_MEMORY_DESCRIPTOR (memory_map, map_size));
grub_abort ();
grub_fatal ("Debug. ");
#endif
/* Release the memory maps. */

View File

@@ -47,18 +47,6 @@ grub_error (grub_err_t n, const char *fmt, ...)
return n;
}
void
grub_fatal (const char *fmt, ...)
{
va_list ap;
va_start (ap, fmt);
grub_vprintf (_(fmt), ap);
va_end (ap);
grub_abort ();
}
void
grub_error_push (void)
{

View File

@@ -24,6 +24,7 @@
#include <grub/time.h>
#include <grub/misc.h>
#include <grub/i386/tsc.h>
#include <grub/i386/cpuid.h>
#include <grub/i386/pit.h>
#include <grub/cpu/io.h>
@@ -35,6 +36,35 @@ static grub_uint64_t tsc_boot_time;
in 32-bit. */
grub_uint32_t grub_tsc_rate;
/* Read the TSC value, which increments with each CPU clock cycle. */
static __inline grub_uint64_t
grub_get_tsc (void)
{
grub_uint32_t lo, hi;
grub_uint32_t a,b,c,d;
/* The CPUID instruction is a 'serializing' instruction, and
avoids out-of-order execution of the RDTSC instruction. */
grub_cpuid (0,a,b,c,d);
/* Read TSC value. We cannot use "=A", since this would use
%rax on x86_64. */
__asm__ __volatile__ ("rdtsc":"=a" (lo), "=d" (hi));
return (((grub_uint64_t) hi) << 32) | lo;
}
static __inline int
grub_cpu_is_tsc_supported (void)
{
grub_uint32_t a,b,c,d;
if (! grub_cpu_is_cpuid_supported ())
return 0;
grub_cpuid(1,a,b,c,d);
return (d & (1 << 4)) != 0;
}
static void
grub_pit_wait (grub_uint16_t tics)
{
@@ -63,7 +93,7 @@ grub_pit_wait (grub_uint16_t tics)
GRUB_PIT_SPEAKER_PORT);
}
grub_uint64_t
static grub_uint64_t
grub_tsc_get_time_ms (void)
{
grub_uint64_t a = grub_get_tsc () - tsc_boot_time;

View File

@@ -664,34 +664,33 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
if (c != '%')
continue;
if (*fmt && *fmt =='-')
if (*fmt =='-')
fmt++;
while (*fmt && grub_isdigit (*fmt))
while (grub_isdigit (*fmt))
fmt++;
if (*fmt && *fmt == '$')
if (*fmt == '$')
fmt++;
if (*fmt && *fmt =='-')
if (*fmt =='-')
fmt++;
while (*fmt && grub_isdigit (*fmt))
while (grub_isdigit (*fmt))
fmt++;
if (*fmt && *fmt =='.')
if (*fmt =='.')
fmt++;
while (*fmt && grub_isdigit (*fmt))
while (grub_isdigit (*fmt))
fmt++;
c = *fmt++;
if (c == 'l')
{
c = *fmt++;
if (c == 'l')
c = *fmt++;
}
c = *fmt++;
if (c == 'l')
c = *fmt++;
switch (c)
{
case 'p':
@@ -706,16 +705,17 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
}
}
enum { INT, WCHAR, LONG, LONGLONG, POINTER } types[count_args];
enum { INT, LONG, LONGLONG, POINTER } types[count_args];
union
{
int i;
grub_uint32_t w;
long l;
long long ll;
void *p;
} args[count_args];
COMPILE_TIME_ASSERT (sizeof (int) == sizeof (grub_uint32_t));
grub_memset (types, 0, sizeof (types));
fmt = fmt0;
@@ -787,21 +787,16 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
case 's':
types[curn] = POINTER;
break;
case 'C':
case 'c':
types[curn] = INT;
break;
case 'C':
types[curn] = WCHAR;
break;
}
}
for (n = 0; n < count_args; n++)
switch (types[n])
{
case WCHAR:
args[n].w = va_arg (args_in, grub_uint32_t);
break;
case POINTER:
args[n].p = va_arg (args_in, void *);
break;
@@ -929,7 +924,7 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
case 'C':
{
grub_uint32_t code = args[curn].w;
grub_uint32_t code = args[curn].i;
int shift;
unsigned mask;
@@ -948,21 +943,11 @@ grub_vsnprintf_real (char *str, grub_size_t max_len, const char *fmt0, va_list a
shift = 12;
mask = 0xe0;
}
else if (code <= 0x1fffff)
else if (code <= 0x10ffff)
{
shift = 18;
mask = 0xf0;
}
else if (code <= 0x3ffffff)
{
shift = 24;
mask = 0xf8;
}
else if (code <= 0x7fffffff)
{
shift = 30;
mask = 0xfc;
}
else
{
code = '?';
@@ -1078,7 +1063,7 @@ grub_xasprintf (const char *fmt, ...)
}
/* Abort GRUB. This function does not return. */
void
static void __attribute__ ((noreturn))
grub_abort (void)
{
grub_printf ("\nAborted.");
@@ -1094,10 +1079,17 @@ grub_abort (void)
grub_exit ();
}
#if ! defined (__APPLE__) && !defined (GRUB_UTIL)
/* GCC emits references to abort(). */
void abort (void) __attribute__ ((alias ("grub_abort")));
#endif
void
grub_fatal (const char *fmt, ...)
{
va_list ap;
va_start (ap, fmt);
grub_vprintf (_(fmt), ap);
va_end (ap);
grub_abort ();
}
#if NEED_REGISTER_FRAME_INFO && !defined(GRUB_UTIL)
void __register_frame_info (void)

154
grub-core/lib/disk.c Normal file
View File

@@ -0,0 +1,154 @@
/*
* GRUB -- GRand Unified Bootloader
* Copyright (C) 2002,2003,2004,2006,2007,2008,2009,2010 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/>.
*/
#include <grub/disk.h>
#include <grub/err.h>
#include <grub/mm.h>
#include <grub/types.h>
#include <grub/partition.h>
#include <grub/misc.h>
#include <grub/time.h>
#include <grub/file.h>
#include <grub/i18n.h>
GRUB_MOD_LICENSE ("GPLv3+");
#include "../kern/disk_common.c"
static void
grub_disk_cache_invalidate (unsigned long dev_id, unsigned long disk_id,
grub_disk_addr_t sector)
{
unsigned cache_index;
struct grub_disk_cache *cache;
sector &= ~(GRUB_DISK_CACHE_SIZE - 1);
cache_index = grub_disk_cache_get_index (dev_id, disk_id, sector);
cache = grub_disk_cache_table + cache_index;
if (cache->dev_id == dev_id && cache->disk_id == disk_id
&& cache->sector == sector && cache->data)
{
cache->lock = 1;
grub_free (cache->data);
cache->data = 0;
cache->lock = 0;
}
}
grub_err_t
grub_disk_write (grub_disk_t disk, grub_disk_addr_t sector,
grub_off_t offset, grub_size_t size, const void *buf)
{
unsigned real_offset;
grub_disk_addr_t aligned_sector;
grub_dprintf ("disk", "Writing `%s'...\n", disk->name);
if (grub_disk_adjust_range (disk, &sector, &offset, size) != GRUB_ERR_NONE)
return -1;
aligned_sector = (sector & ~((1 << (disk->log_sector_size
- GRUB_DISK_SECTOR_BITS)) - 1));
real_offset = offset + ((sector - aligned_sector) << GRUB_DISK_SECTOR_BITS);
sector = aligned_sector;
while (size)
{
if (real_offset != 0 || (size < (1U << disk->log_sector_size)
&& size != 0))
{
char *tmp_buf;
grub_size_t len;
grub_partition_t part;
tmp_buf = grub_malloc (1 << disk->log_sector_size);
if (!tmp_buf)
return grub_errno;
part = disk->partition;
disk->partition = 0;
if (grub_disk_read (disk, sector,
0, (1 << disk->log_sector_size), tmp_buf)
!= GRUB_ERR_NONE)
{
disk->partition = part;
grub_free (tmp_buf);
goto finish;
}
disk->partition = part;
len = (1 << disk->log_sector_size) - real_offset;
if (len > size)
len = size;
grub_memcpy (tmp_buf + real_offset, buf, len);
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
if ((disk->dev->write) (disk, transform_sector (disk, sector),
1, tmp_buf) != GRUB_ERR_NONE)
{
grub_free (tmp_buf);
goto finish;
}
grub_free (tmp_buf);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
buf = (const char *) buf + len;
size -= len;
real_offset = 0;
}
else
{
grub_size_t len;
grub_size_t n;
len = size & ~((1 << disk->log_sector_size) - 1);
n = size >> disk->log_sector_size;
if ((disk->dev->write) (disk, transform_sector (disk, sector),
n, buf) != GRUB_ERR_NONE)
goto finish;
while (n--)
{
grub_disk_cache_invalidate (disk->dev->id, disk->id, sector);
sector += (1 << (disk->log_sector_size - GRUB_DISK_SECTOR_BITS));
}
buf = (const char *) buf + len;
size -= len;
}
}
finish:
return grub_errno;
}
GRUB_MOD_INIT(disk)
{
grub_disk_write_weak = grub_disk_write;
}
GRUB_MOD_FINI(disk)
{
grub_disk_write_weak = NULL;
}

View File

@@ -70,7 +70,7 @@ static struct legacy_command legacy_commands[] =
"Print the blocklist notation of the file FILE."},
{"boot", "boot\n", NULL, 0, 0, {}, 0, 0,
"Boot the OS/chain-loader which has been loaded."},
{"bootp", "net_bootp; net_ls_addr; if [ x%s = x--with-configfile ]; then "
{"bootp", "net_bootp; net_ls_addr; echo $\"" N_("Default server is ${net_default_server}") "\"; if [ x%s = x--with-configfile ]; then "
"if net_get_dhcp_option configfile_name pxe 150 string; then "
"configfile $configfile_name; fi; fi\n", NULL, 0, 1,
{TYPE_WITH_CONFIGFILE_OPTION}, FLAG_IGNORE_REST, "[--with-configfile]",
@@ -385,6 +385,29 @@ adjust_file (const char *in, grub_size_t len)
if (*ptr == '\'' || *ptr == '\\')
overhead++;
comma = ptr;
if (*comma == ')' && comma - in == 3
&& in[1] == 'n' && in[2] == 'd')
{
rest = comma + 1;
for (ptr = rest; ptr < in + len && *ptr; ptr++)
if (*ptr == '\'' || *ptr == '\\')
overhead++;
ret = grub_malloc (ptr - in + overhead + 15);
if (!ret)
return NULL;
outptr = grub_stpcpy (ret, "(tftp)");;
for (ptr = rest; ptr < in + len; ptr++)
{
if (*ptr == '\'' || *ptr == '\\')
*outptr++ = '\\';
*outptr++ = *ptr;
}
*outptr = 0;
return ret;
}
if (*comma != ',')
return grub_legacy_escape (in, len);
part = grub_strtoull (comma + 1, (char **) &rest, 0);
@@ -398,7 +421,7 @@ adjust_file (const char *in, grub_size_t len)
overhead++;
/* 35 is enough for any 2 numbers. */
ret = grub_malloc (ptr - in + overhead + 35);
ret = grub_malloc (ptr - in + overhead + 35 + 5);
if (!ret)
return NULL;

View File

@@ -115,7 +115,7 @@ void _gcry_log_bug (const char *fmt, ...)
grub_vprintf (fmt, args);
va_end (args);
grub_refresh ();
grub_abort ();
grub_fatal ("gcrypt bug");
}
gcry_err_code_t

View File

@@ -25,6 +25,7 @@
#include <grub/loader.h>
#include <grub/autoefi.h>
#include <grub/i386/tsc.h>
#include <grub/i386/cpuid.h>
#include <grub/efi/api.h>
#include <grub/i386/pit.h>
#include <grub/misc.h>
@@ -125,66 +126,22 @@ guessfsb (void)
{
const grub_uint64_t sane_value = 100000000;
grub_uint32_t manufacturer[3], max_cpuid, capabilities, msrlow;
grub_uint32_t a, b, d;
if (! grub_cpu_is_cpuid_supported ())
return sane_value;
#ifdef __APPLE__
asm volatile ("movl $0, %%eax\n"
#ifdef __x86_64__
"push %%rbx\n"
#else
"push %%ebx\n"
#endif
"cpuid\n"
#ifdef __x86_64__
"pop %%rbx\n"
#else
"pop %%ebx\n"
#endif
: "=a" (max_cpuid),
"=d" (manufacturer[1]), "=c" (manufacturer[2]));
/* Only Intel for now is done. */
if (grub_memcmp (manufacturer + 1, "ineIntel", 12) != 0)
return sane_value;
#else
asm volatile ("movl $0, %%eax\n"
"cpuid"
: "=a" (max_cpuid), "=b" (manufacturer[0]),
"=d" (manufacturer[1]), "=c" (manufacturer[2]));
grub_cpuid (0, max_cpuid, manufacturer[0], manufacturer[2], manufacturer[1]);
/* Only Intel for now is done. */
if (grub_memcmp (manufacturer, "GenuineIntel", 12) != 0)
return sane_value;
#endif
/* Check Speedstep. */
if (max_cpuid < 1)
return sane_value;
#ifdef __APPLE__
asm volatile ("movl $1, %%eax\n"
#ifdef __x86_64__
"push %%rbx\n"
#else
"push %%ebx\n"
#endif
"cpuid\n"
#ifdef __x86_64__
"pop %%rbx\n"
#else
"pop %%ebx\n"
#endif
: "=c" (capabilities):
: "%rax", "%rdx");
#else
asm volatile ("movl $1, %%eax\n"
"cpuid"
: "=c" (capabilities):
: "%rax", "%rbx", "%rdx");
#endif
grub_cpuid (1, a, b, capabilities, d);
if (! (capabilities & (1 << 7)))
return sane_value;

View File

@@ -29,7 +29,7 @@
#include <grub/video.h>
#include <grub/i386/pc/int.h>
#include <grub/i18n.h>
#include <grub/cpu/tsc.h>
#include <grub/cpu/cpuid.h>
GRUB_MOD_LICENSE ("GPLv3+");
@@ -58,11 +58,6 @@ real2pm (grub_vbe_farptr_t ptr)
+ ((unsigned long) ptr & 0x0000FFFF));
}
#define cpuid(num,a,b,c,d) \
asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1" \
: "=a" (a), "=r" (b), "=c" (c), "=d" (d) \
: "0" (num))
#define rdmsr(num,a,d) \
asm volatile ("rdmsr" : "=a" (a), "=d" (d) : "c" (num))
@@ -136,7 +131,7 @@ grub_vbe_enable_mtrr (grub_uint8_t *base, grub_size_t size)
if (! grub_cpu_is_cpuid_supported ())
return;
cpuid (1, eax, ebx, ecx, edx);
grub_cpuid (1, eax, ebx, ecx, edx);
features = edx;
if (! (features & 0x00001000)) /* MTRR */
return;
@@ -147,11 +142,11 @@ grub_vbe_enable_mtrr (grub_uint8_t *base, grub_size_t size)
return;
var_mtrrs = (mtrrcap & 0xFF);
cpuid (0x80000000, eax, ebx, ecx, edx);
grub_cpuid (0x80000000, eax, ebx, ecx, edx);
max_extended_cpuid = eax;
if (max_extended_cpuid >= 0x80000008)
{
cpuid (0x80000008, eax, ebx, ecx, edx);
grub_cpuid (0x80000008, eax, ebx, ecx, edx);
maxphyaddr = (eax & 0xFF);
}
else

View File

@@ -40,7 +40,8 @@ struct grub_archelp_ops
grub_err_t
(*find_file) (struct grub_archelp_data *data, char **name,
grub_int32_t *mtime,
grub_archelp_mode_t *mode);
grub_archelp_mode_t *mode,
grub_uint64_t *size);
char *
(*get_link_target) (struct grub_archelp_data *data);

View File

@@ -193,11 +193,17 @@ grub_err_t EXPORT_FUNC(grub_disk_read) (grub_disk_t disk,
grub_off_t offset,
grub_size_t size,
void *buf);
grub_err_t EXPORT_FUNC(grub_disk_write) (grub_disk_t disk,
grub_disk_addr_t sector,
grub_off_t offset,
grub_size_t size,
const void *buf);
grub_err_t grub_disk_write (grub_disk_t disk,
grub_disk_addr_t sector,
grub_off_t offset,
grub_size_t size,
const void *buf);
extern grub_err_t (*EXPORT_VAR(grub_disk_write_weak)) (grub_disk_t disk,
grub_disk_addr_t sector,
grub_off_t offset,
grub_size_t size,
const void *buf);
grub_uint64_t EXPORT_FUNC(grub_disk_get_size) (grub_disk_t disk);
@@ -221,6 +227,18 @@ grub_stop_disk_firmware (void)
}
}
/* Disk cache. */
struct grub_disk_cache
{
enum grub_disk_dev_id dev_id;
unsigned long disk_id;
grub_disk_addr_t sector;
char *data;
int lock;
};
extern struct grub_disk_cache EXPORT_VAR(grub_disk_cache_table)[GRUB_DISK_CACHE_NUM];
#if defined (GRUB_UTIL)
void grub_lvm_init (void);
void grub_ldm_init (void);

View File

@@ -39,6 +39,7 @@ struct grub_dirhook_info
unsigned mtimeset:1;
unsigned case_insensitive:1;
grub_int32_t mtime;
grub_off_t size;
};
typedef int (*grub_fs_dir_hook_t) (const char *filename,

View File

@@ -21,4 +21,64 @@
extern unsigned char grub_cpuid_has_longmode;
#ifdef __x86_64__
static __inline int
grub_cpu_is_cpuid_supported (void)
{
grub_uint64_t id_supported;
__asm__ ("pushfq\n\t"
"popq %%rax /* Get EFLAGS into EAX */\n\t"
"movq %%rax, %%rcx /* Save original flags in ECX */\n\t"
"xorq $0x200000, %%rax /* Flip ID bit in EFLAGS */\n\t"
"pushq %%rax /* Store modified EFLAGS on stack */\n\t"
"popfq /* Replace current EFLAGS */\n\t"
"pushfq /* Read back the EFLAGS */\n\t"
"popq %%rax /* Get EFLAGS into EAX */\n\t"
"xorq %%rcx, %%rax /* Check if flag could be modified */\n\t"
: "=a" (id_supported)
: /* No inputs. */
: /* Clobbered: */ "%rcx");
return id_supported != 0;
}
#else
static __inline int
grub_cpu_is_cpuid_supported (void)
{
grub_uint32_t id_supported;
__asm__ ("pushfl\n\t"
"popl %%eax /* Get EFLAGS into EAX */\n\t"
"movl %%eax, %%ecx /* Save original flags in ECX */\n\t"
"xorl $0x200000, %%eax /* Flip ID bit in EFLAGS */\n\t"
"pushl %%eax /* Store modified EFLAGS on stack */\n\t"
"popfl /* Replace current EFLAGS */\n\t"
"pushfl /* Read back the EFLAGS */\n\t"
"popl %%eax /* Get EFLAGS into EAX */\n\t"
"xorl %%ecx, %%eax /* Check if flag could be modified */\n\t"
: "=a" (id_supported)
: /* No inputs. */
: /* Clobbered: */ "%rcx");
return id_supported != 0;
}
#endif
#ifdef __PIC__
#define grub_cpuid(num,a,b,c,d) \
asm volatile ("xchgl %%ebx, %1; cpuid; xchgl %%ebx, %1" \
: "=a" (a), "=r" (b), "=c" (c), "=d" (d) \
: "0" (num))
#else
#define grub_cpuid(num,a,b,c,d) \
asm volatile ("cpuid" \
: "=a" (a), "=b" (b), "=c" (c), "=d" (d) \
: "0" (num))
#endif
#endif

View File

@@ -21,122 +21,7 @@
#include <grub/types.h>
/* Read the TSC value, which increments with each CPU clock cycle. */
static __inline grub_uint64_t
grub_get_tsc (void)
{
grub_uint32_t lo, hi;
/* The CPUID instruction is a 'serializing' instruction, and
avoids out-of-order execution of the RDTSC instruction. */
#ifdef __APPLE__
__asm__ __volatile__ ("xorl %%eax, %%eax\n\t"
#ifdef __x86_64__
"push %%rbx\n"
#else
"push %%ebx\n"
#endif
"cpuid\n"
#ifdef __x86_64__
"pop %%rbx\n"
#else
"pop %%ebx\n"
#endif
:::"%rax", "%rcx", "%rdx");
#else
__asm__ __volatile__ ("xorl %%eax, %%eax\n\t"
"cpuid":::"%rax", "%rbx", "%rcx", "%rdx");
#endif
/* Read TSC value. We cannot use "=A", since this would use
%rax on x86_64. */
__asm__ __volatile__ ("rdtsc":"=a" (lo), "=d" (hi));
return (((grub_uint64_t) hi) << 32) | lo;
}
#ifdef __x86_64__
static __inline int
grub_cpu_is_cpuid_supported (void)
{
grub_uint64_t id_supported;
__asm__ ("pushfq\n\t"
"popq %%rax /* Get EFLAGS into EAX */\n\t"
"movq %%rax, %%rcx /* Save original flags in ECX */\n\t"
"xorq $0x200000, %%rax /* Flip ID bit in EFLAGS */\n\t"
"pushq %%rax /* Store modified EFLAGS on stack */\n\t"
"popfq /* Replace current EFLAGS */\n\t"
"pushfq /* Read back the EFLAGS */\n\t"
"popq %%rax /* Get EFLAGS into EAX */\n\t"
"xorq %%rcx, %%rax /* Check if flag could be modified */\n\t"
: "=a" (id_supported)
: /* No inputs. */
: /* Clobbered: */ "%rcx");
return id_supported != 0;
}
#else
static __inline int
grub_cpu_is_cpuid_supported (void)
{
grub_uint32_t id_supported;
__asm__ ("pushfl\n\t"
"popl %%eax /* Get EFLAGS into EAX */\n\t"
"movl %%eax, %%ecx /* Save original flags in ECX */\n\t"
"xorl $0x200000, %%eax /* Flip ID bit in EFLAGS */\n\t"
"pushl %%eax /* Store modified EFLAGS on stack */\n\t"
"popfl /* Replace current EFLAGS */\n\t"
"pushfl /* Read back the EFLAGS */\n\t"
"popl %%eax /* Get EFLAGS into EAX */\n\t"
"xorl %%ecx, %%eax /* Check if flag could be modified */\n\t"
: "=a" (id_supported)
: /* No inputs. */
: /* Clobbered: */ "%rcx");
return id_supported != 0;
}
#endif
static __inline int
grub_cpu_is_tsc_supported (void)
{
if (! grub_cpu_is_cpuid_supported ())
return 0;
grub_uint32_t features;
#ifdef __APPLE__
__asm__ ("movl $1, %%eax\n\t"
#ifdef __x86_64__
"push %%rbx\n"
#else
"push %%ebx\n"
#endif
"cpuid\n"
#ifdef __x86_64__
"pop %%rbx\n"
#else
"pop %%ebx\n"
#endif
: "=d" (features)
: /* No inputs. */
: /* Clobbered: */ "%rax", "%rcx");
#else
__asm__ ("movl $1, %%eax\n\t"
"cpuid\n"
: "=d" (features)
: /* No inputs. */
: /* Clobbered: */ "%rax", "%rbx", "%rcx");
#endif
return (features & (1 << 4)) != 0;
}
void grub_tsc_init (void);
grub_uint64_t grub_tsc_get_time_ms (void);
/* In ms per 2^32 ticks. */
extern grub_uint32_t EXPORT_VAR(grub_tsc_rate);

View File

@@ -375,7 +375,6 @@ char *EXPORT_FUNC(grub_xasprintf) (const char *fmt, ...)
__attribute__ ((format (GNU_PRINTF, 1, 2))) WARN_UNUSED_RESULT;
char *EXPORT_FUNC(grub_xvasprintf) (const char *fmt, va_list args) WARN_UNUSED_RESULT;
void EXPORT_FUNC(grub_exit) (void) __attribute__ ((noreturn));
void EXPORT_FUNC(grub_abort) (void) __attribute__ ((noreturn));
grub_uint64_t EXPORT_FUNC(grub_divmod64) (grub_uint64_t n,
grub_uint64_t d,
grub_uint64_t *r);

View File

@@ -65,7 +65,7 @@ argument () {
shift
if test $# -eq 0; then
gettext_printf "%s: option requires an argument -- \`%s'\n" "$0" "$opt" 1>&2
gettext_printf "%s: option requires an argument -- \`%s'\n" "$self" "$opt" 1>&2
exit 1
fi
echo $1

View File

@@ -116,6 +116,9 @@ fi
memdisk_dir="`mktemp -d "${TMPDIR:-/tmp}/tmp.XXXXXXXXXX"`" || exit 1
grub_install_files "${source_directory}" "${memdisk_dir}"/boot/grub "${grub_modinfo_target_cpu}-${grub_modinfo_platform}"
for file in $source; do
cp -f "$file" "${memdisk_dir}"/"$file";
done
memdisk_img=`mktemp "${TMPDIR:-/tmp}/tmp.XXXXXXXXXX"` || exit 1

View File

@@ -65,7 +65,7 @@ argument () {
shift
if test $# -eq 0; then
gettext_printf "%s: option requires an argument -- \`%s'\n" "$0" "$opt" 1>&2
gettext_printf "%s: option requires an argument -- \`%s'\n" "$self" "$opt" 1>&2
exit 1
fi
echo $1

View File

@@ -63,7 +63,7 @@ argument () {
shift
if test $# -eq 0; then
gettext_printf "%s: option requires an argument -- \`%s'\n" "$0" "$opt" 1>&2
gettext_printf "%s: option requires an argument -- \`%s'\n" "$self" "$opt" 1>&2
exit 1
fi
echo $1

View File

@@ -191,7 +191,7 @@ EOF
EOF
# Gettext variables and module
if [ "x${LANG}" != "xC" ] ; then
if [ "x${LANG}" != "xC" ] && [ "x${LANG}" != "x" ]; then
cat << EOF
set locale_dir=\$prefix/locale
set lang=${grub_lang}