mirror of
https://git.savannah.gnu.org/git/grub.git
synced 2026-10-29 02:31:05 +00:00
Compare commits
1
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e7f405abb3 |
No files matched your search
@@ -1,21 +1,3 @@
|
|||||||
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>
|
2013-10-26 BVK Chaitanya <bvk.groups@gmail.com>
|
||||||
|
|
||||||
* docs/osdetect.cfg: New file.
|
* docs/osdetect.cfg: New file.
|
||||||
|
|||||||
@@ -146,7 +146,6 @@ library = {
|
|||||||
common = grub-core/partmap/sunpc.c;
|
common = grub-core/partmap/sunpc.c;
|
||||||
common = grub-core/partmap/bsdlabel.c;
|
common = grub-core/partmap/bsdlabel.c;
|
||||||
common = grub-core/partmap/dfly.c;
|
common = grub-core/partmap/dfly.c;
|
||||||
common = grub-core/partmap/dasd.c;
|
|
||||||
common = grub-core/script/function.c;
|
common = grub-core/script/function.c;
|
||||||
common = grub-core/script/lexer.c;
|
common = grub-core/script/lexer.c;
|
||||||
common = grub-core/script/main.c;
|
common = grub-core/script/main.c;
|
||||||
|
|||||||
@@ -90,7 +90,6 @@ case "$target_cpu" in
|
|||||||
i[[3456]]86) target_cpu=i386 ;;
|
i[[3456]]86) target_cpu=i386 ;;
|
||||||
amd64) target_cpu=x86_64 ;;
|
amd64) target_cpu=x86_64 ;;
|
||||||
sparc) target_cpu=sparc64 ;;
|
sparc) target_cpu=sparc64 ;;
|
||||||
s390x) target_cpu=s390 ;;
|
|
||||||
mipsel|mips64el)
|
mipsel|mips64el)
|
||||||
target_cpu=mipsel;
|
target_cpu=mipsel;
|
||||||
machine_CPPFLAGS="$machine_CPPFLAGS -DGRUB_CPU_MIPSEL=1";
|
machine_CPPFLAGS="$machine_CPPFLAGS -DGRUB_CPU_MIPSEL=1";
|
||||||
@@ -123,7 +122,6 @@ if test "x$with_platform" = x; then
|
|||||||
mips-*) platform=arc ;;
|
mips-*) platform=arc ;;
|
||||||
ia64-*) platform=efi ;;
|
ia64-*) platform=efi ;;
|
||||||
arm-*) platform=uboot ;;
|
arm-*) platform=uboot ;;
|
||||||
s390-* | s390x-*) platform=mainframe ;;
|
|
||||||
*) AC_MSG_ERROR([unsupported CPU: "$target_cpu"]) ;;
|
*) AC_MSG_ERROR([unsupported CPU: "$target_cpu"]) ;;
|
||||||
esac
|
esac
|
||||||
else
|
else
|
||||||
@@ -161,7 +159,6 @@ case "$target_cpu"-"$platform" in
|
|||||||
mipsel-loongson) ;;
|
mipsel-loongson) ;;
|
||||||
arm-uboot) ;;
|
arm-uboot) ;;
|
||||||
arm-efi) ;;
|
arm-efi) ;;
|
||||||
s390-mainframe) ;;
|
|
||||||
*-emu) ;;
|
*-emu) ;;
|
||||||
*) AC_MSG_ERROR([platform "$platform" is not supported for target CPU "$target_cpu"]) ;;
|
*) AC_MSG_ERROR([platform "$platform" is not supported for target CPU "$target_cpu"]) ;;
|
||||||
esac
|
esac
|
||||||
@@ -1334,7 +1331,6 @@ AM_CONDITIONAL([COND_mips_qemu_mips], [test "(" x$target_cpu = xmips -o x$target
|
|||||||
AM_CONDITIONAL([COND_mips_arc], [test "(" x$target_cpu = xmips -o x$target_cpu = xmipsel ")" -a x$platform = xarc])
|
AM_CONDITIONAL([COND_mips_arc], [test "(" x$target_cpu = xmips -o x$target_cpu = xmipsel ")" -a x$platform = xarc])
|
||||||
AM_CONDITIONAL([COND_sparc64_ieee1275], [test x$target_cpu = xsparc64 -a x$platform = xieee1275])
|
AM_CONDITIONAL([COND_sparc64_ieee1275], [test x$target_cpu = xsparc64 -a x$platform = xieee1275])
|
||||||
AM_CONDITIONAL([COND_powerpc_ieee1275], [test x$target_cpu = xpowerpc -a x$platform = xieee1275])
|
AM_CONDITIONAL([COND_powerpc_ieee1275], [test x$target_cpu = xpowerpc -a x$platform = xieee1275])
|
||||||
AM_CONDITIONAL([COND_s390_mainframe], [test x$target_cpu = xs390 -a x$platform = xmainframe])
|
|
||||||
AM_CONDITIONAL([COND_mips], [test x$target_cpu = xmips -o x$target_cpu = xmipsel])
|
AM_CONDITIONAL([COND_mips], [test x$target_cpu = xmips -o x$target_cpu = xmipsel])
|
||||||
AM_CONDITIONAL([COND_mipsel], [test x$target_cpu = xmipsel])
|
AM_CONDITIONAL([COND_mipsel], [test x$target_cpu = xmipsel])
|
||||||
AM_CONDITIONAL([COND_mipseb], [test x$target_cpu = xmips])
|
AM_CONDITIONAL([COND_mipseb], [test x$target_cpu = xmips])
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ GRUB_PLATFORMS = [ "emu", "i386_pc", "i386_efi", "i386_qemu", "i386_coreboot",
|
|||||||
"i386_multiboot", "i386_ieee1275", "x86_64_efi",
|
"i386_multiboot", "i386_ieee1275", "x86_64_efi",
|
||||||
"mips_loongson", "sparc64_ieee1275",
|
"mips_loongson", "sparc64_ieee1275",
|
||||||
"powerpc_ieee1275", "mips_arc", "ia64_efi",
|
"powerpc_ieee1275", "mips_arc", "ia64_efi",
|
||||||
"mips_qemu_mips", "arm_uboot", "arm_efi", "s390_mainframe" ]
|
"mips_qemu_mips", "arm_uboot", "arm_efi" ]
|
||||||
|
|
||||||
GROUPS = {}
|
GROUPS = {}
|
||||||
|
|
||||||
@@ -37,7 +37,6 @@ GROUPS["mips"] = [ "mips_loongson", "mips_qemu_mips", "mips_arc" ]
|
|||||||
GROUPS["sparc64"] = [ "sparc64_ieee1275" ]
|
GROUPS["sparc64"] = [ "sparc64_ieee1275" ]
|
||||||
GROUPS["powerpc"] = [ "powerpc_ieee1275" ]
|
GROUPS["powerpc"] = [ "powerpc_ieee1275" ]
|
||||||
GROUPS["arm"] = [ "arm_uboot", "arm_efi" ]
|
GROUPS["arm"] = [ "arm_uboot", "arm_efi" ]
|
||||||
GROUPS["s390"] = [ "s390_mainframe" ]
|
|
||||||
|
|
||||||
# Groups based on firmware
|
# Groups based on firmware
|
||||||
GROUPS["efi"] = [ "i386_efi", "x86_64_efi", "ia64_efi", "arm_efi" ]
|
GROUPS["efi"] = [ "i386_efi", "x86_64_efi", "ia64_efi", "arm_efi" ]
|
||||||
|
|||||||
@@ -78,7 +78,6 @@ kernel = {
|
|||||||
sparc64_ieee1275_ldflags = '-Wl,-Ttext,0x4400';
|
sparc64_ieee1275_ldflags = '-Wl,-Ttext,0x4400';
|
||||||
mips_arc_ldflags = '-Wl,-Ttext,$(TARGET_LINK_ADDR)';
|
mips_arc_ldflags = '-Wl,-Ttext,$(TARGET_LINK_ADDR)';
|
||||||
mips_qemu_mips_ldflags = '-Wl,-Ttext,0x80200000';
|
mips_qemu_mips_ldflags = '-Wl,-Ttext,0x80200000';
|
||||||
s390_mainframe_ldflags = '-Wl,-Ttext,0x8000';
|
|
||||||
|
|
||||||
mips_arc_cppflags = '-DGRUB_DECOMPRESSOR_LINK_ADDR=$(TARGET_DECOMPRESSOR_LINK_ADDR)';
|
mips_arc_cppflags = '-DGRUB_DECOMPRESSOR_LINK_ADDR=$(TARGET_DECOMPRESSOR_LINK_ADDR)';
|
||||||
mips_loongson_cppflags = '-DUSE_ASCII_FALLBACK';
|
mips_loongson_cppflags = '-DUSE_ASCII_FALLBACK';
|
||||||
@@ -1738,11 +1737,6 @@ module = {
|
|||||||
common = partmap/dfly.c;
|
common = partmap/dfly.c;
|
||||||
};
|
};
|
||||||
|
|
||||||
module = {
|
|
||||||
name = part_dasd;
|
|
||||||
common = partmap/dasd.c;
|
|
||||||
};
|
|
||||||
|
|
||||||
module = {
|
module = {
|
||||||
name = msdospart;
|
name = msdospart;
|
||||||
common = parttool/msdospart.c;
|
common = parttool/msdospart.c;
|
||||||
@@ -2146,3 +2140,8 @@ module = {
|
|||||||
name = progress;
|
name = progress;
|
||||||
common = lib/progress.c;
|
common = lib/progress.c;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
module = {
|
||||||
|
name = crypto_devmapper;
|
||||||
|
common = disk/devmapper.c;
|
||||||
|
};
|
||||||
@@ -29,6 +29,11 @@
|
|||||||
|
|
||||||
GRUB_MOD_LICENSE ("GPLv3+");
|
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[] =
|
static const struct grub_arg_option options[] =
|
||||||
{
|
{
|
||||||
/* TRANSLATORS: "(default)" at the end means that this option is used if
|
/* TRANSLATORS: "(default)" at the end means that this option is used if
|
||||||
@@ -73,18 +78,18 @@ GRUB_MOD_INIT(cpuid)
|
|||||||
goto done;
|
goto done;
|
||||||
|
|
||||||
/* Check the highest input value for eax. */
|
/* Check the highest input value for eax. */
|
||||||
grub_cpuid (0, eax, ebx, ecx, edx);
|
cpuid (0, eax, ebx, ecx, edx);
|
||||||
/* We only look at the first four characters. */
|
/* We only look at the first four characters. */
|
||||||
max_level = eax;
|
max_level = eax;
|
||||||
if (max_level == 0)
|
if (max_level == 0)
|
||||||
goto done;
|
goto done;
|
||||||
|
|
||||||
grub_cpuid (0x80000000, eax, ebx, ecx, edx);
|
cpuid (0x80000000, eax, ebx, ecx, edx);
|
||||||
ext_level = eax;
|
ext_level = eax;
|
||||||
if (ext_level < 0x80000000)
|
if (ext_level < 0x80000000)
|
||||||
goto done;
|
goto done;
|
||||||
|
|
||||||
grub_cpuid (0x80000001, eax, ebx, ecx, edx);
|
cpuid (0x80000001, eax, ebx, ecx, edx);
|
||||||
grub_cpuid_has_longmode = !!(edx & bit_LM);
|
grub_cpuid_has_longmode = !!(edx & bit_LM);
|
||||||
done:
|
done:
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -0,0 +1,414 @@
|
|||||||
|
/*
|
||||||
|
* devmapper.c - Device mapper (w/ crypto support)
|
||||||
|
*
|
||||||
|
* Copyright (C) 2007 Simon Peter <dn.tlp@gmx.net>
|
||||||
|
* Thanks to Raoul Boenisch <jkl345@gmx.net> for the initial idea.
|
||||||
|
*/
|
||||||
|
/*
|
||||||
|
* GRUB -- GRand Unified Bootloader
|
||||||
|
* Copyright (C) 2003,2007 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/types.h>
|
||||||
|
#include <grub/misc.h>
|
||||||
|
#include <grub/mm.h>
|
||||||
|
#include <grub/err.h>
|
||||||
|
#include <grub/dl.h>
|
||||||
|
#include <grub/normal.h>
|
||||||
|
#include <grub/extcmd.h>
|
||||||
|
#include <grub/disk.h>
|
||||||
|
#include <grub/crypto.h>
|
||||||
|
|
||||||
|
#define DEFAULT_HASH "ripemd160"
|
||||||
|
#define DEFAULT_CIPHER "aes-cbc"
|
||||||
|
#define MAX_KEYSIZE 64
|
||||||
|
#define MAX_PASSPHRASE 256
|
||||||
|
|
||||||
|
#define MIN(a, b) (a < b ? a : b)
|
||||||
|
|
||||||
|
struct grub_crypto
|
||||||
|
{
|
||||||
|
char *devname, *source_devname;
|
||||||
|
int has_partitions;
|
||||||
|
grub_crypto_cipher_handle_t cipher;
|
||||||
|
grub_disk_t srcdisk;
|
||||||
|
int keysize;
|
||||||
|
|
||||||
|
struct grub_crypto *next;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct grub_crypto *grub_crypto_t;
|
||||||
|
|
||||||
|
struct crypto_private
|
||||||
|
{
|
||||||
|
grub_crypto_t crypto;
|
||||||
|
grub_disk_t srcdisk;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct crypto_private *crypto_private_t;
|
||||||
|
|
||||||
|
static grub_crypto_t crypto_list = NULL;
|
||||||
|
|
||||||
|
/* Delete a registered crypto device. */
|
||||||
|
static grub_err_t
|
||||||
|
delete_crypto (const char *name)
|
||||||
|
{
|
||||||
|
grub_crypto_t dev, *prev;
|
||||||
|
|
||||||
|
/* Search for the device */
|
||||||
|
for (dev = crypto_list, prev = &crypto_list; dev;
|
||||||
|
prev = &dev->next, dev = dev->next)
|
||||||
|
if (grub_strcmp (dev->devname, name) == 0)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!dev)
|
||||||
|
return grub_error (GRUB_ERR_BAD_DEVICE, "Device not found");
|
||||||
|
|
||||||
|
/* Remove the device from the list */
|
||||||
|
*prev = dev->next;
|
||||||
|
grub_free (dev->devname);
|
||||||
|
grub_free (dev->source_devname);
|
||||||
|
grub_crypto_cipher_close (dev->cipher);
|
||||||
|
grub_free (dev);
|
||||||
|
|
||||||
|
return GRUB_ERR_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Hashes a passphrase into a key and stores it with cipher. */
|
||||||
|
static gcry_err_code_t
|
||||||
|
set_passphrase (grub_crypto_t dev, const gcry_md_spec_t *hashparams,
|
||||||
|
const char *passphrase)
|
||||||
|
{
|
||||||
|
grub_uint8_t hash[MAX_KEYSIZE * 2], *key = hash;
|
||||||
|
char *p;
|
||||||
|
unsigned int round, i, size = dev->keysize;
|
||||||
|
unsigned int len;
|
||||||
|
|
||||||
|
/* Need no passphrase if there's no key */
|
||||||
|
if (size == 0)
|
||||||
|
return GPG_ERR_INV_KEYLEN;
|
||||||
|
|
||||||
|
/* Hack to support the "none" hash */
|
||||||
|
if (hashparams)
|
||||||
|
len = hashparams->mdlen;
|
||||||
|
else
|
||||||
|
len = grub_strlen (passphrase);
|
||||||
|
|
||||||
|
if (size > MAX_KEYSIZE || len > MAX_KEYSIZE)
|
||||||
|
return GPG_ERR_INV_KEYLEN;
|
||||||
|
|
||||||
|
p = grub_malloc (grub_strlen (passphrase) + 2 + size / len);
|
||||||
|
if (!p)
|
||||||
|
return grub_errno;
|
||||||
|
|
||||||
|
for (round = 0; size; round++, key += len, size -= len)
|
||||||
|
{
|
||||||
|
/* hack from hashalot to avoid null bytes in key */
|
||||||
|
for (i = 0; i < round; i++)
|
||||||
|
p[i] = 'A';
|
||||||
|
|
||||||
|
grub_strcpy (p + i, passphrase);
|
||||||
|
|
||||||
|
if (len > size)
|
||||||
|
len = size;
|
||||||
|
|
||||||
|
grub_crypto_hash (hashparams, key, p, grub_strlen (p));
|
||||||
|
}
|
||||||
|
|
||||||
|
return grub_crypto_cipher_set_key (dev->cipher, hash, size);
|
||||||
|
}
|
||||||
|
|
||||||
|
/***** GRUB command line interface *****************************************/
|
||||||
|
|
||||||
|
|
||||||
|
static const struct grub_arg_option options[] = {
|
||||||
|
{"delete", 'd', 0, "delete the crypto device entry", 0, ARG_TYPE_NONE},
|
||||||
|
{"partitions", 'p', 0, "set that the device has partitions", 0,
|
||||||
|
ARG_TYPE_NONE},
|
||||||
|
{"cipher", 'c', 0, "set cipher (default=" DEFAULT_CIPHER ")", 0,
|
||||||
|
ARG_TYPE_STRING},
|
||||||
|
{"hash", 'h', 0, "set hash function (default=" DEFAULT_HASH ")", 0,
|
||||||
|
ARG_TYPE_STRING},
|
||||||
|
{"passphrase", 'P', 0, "set decryption passphrase", 0, ARG_TYPE_STRING},
|
||||||
|
{"keysize", 'k', 0, "set key size (default is cipher specific)", 0,
|
||||||
|
ARG_TYPE_INT},
|
||||||
|
{0, 0, 0, 0, 0, 0}
|
||||||
|
};
|
||||||
|
|
||||||
|
static grub_err_t
|
||||||
|
grub_cmd_devmap (grub_extcmd_t cmd, int argc, char **args)
|
||||||
|
{
|
||||||
|
grub_disk_t disk;
|
||||||
|
grub_crypto_t newdev;
|
||||||
|
const char *cipher, *hash;
|
||||||
|
const gcry_md_spec_t *hashparams;
|
||||||
|
grub_err_t err = GRUB_ERR_NONE;
|
||||||
|
char *passphrase = "";
|
||||||
|
/* char cmdphrase[MAX_PASSPHRASE]; */
|
||||||
|
const gcry_cipher_spec_t *ciph;
|
||||||
|
struct grub_arg_list *state = cmd->state;
|
||||||
|
|
||||||
|
if (argc < 1)
|
||||||
|
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Device name required");
|
||||||
|
|
||||||
|
/* Check whether delete is requested */
|
||||||
|
if (state[0].set)
|
||||||
|
return delete_crypto (args[0]);
|
||||||
|
|
||||||
|
if (argc < 2)
|
||||||
|
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Source device name required");
|
||||||
|
|
||||||
|
/*** Create device is requested ***/
|
||||||
|
|
||||||
|
/* Choke on already existing devices */
|
||||||
|
for (newdev = crypto_list; newdev != NULL; newdev = newdev->next)
|
||||||
|
if (grub_strcmp (newdev->devname, args[0]) == 0)
|
||||||
|
return grub_error (GRUB_ERR_BAD_ARGUMENT, "Device already exists");
|
||||||
|
|
||||||
|
/* Check whether source device can be opened */
|
||||||
|
disk = grub_disk_open (args[1]);
|
||||||
|
if (!disk)
|
||||||
|
return grub_errno;
|
||||||
|
grub_disk_close (disk);
|
||||||
|
|
||||||
|
/* Parse remaining options */
|
||||||
|
if (state[2].set)
|
||||||
|
cipher = state[2].arg;
|
||||||
|
else
|
||||||
|
cipher = DEFAULT_CIPHER;
|
||||||
|
if (state[3].set)
|
||||||
|
hash = state[3].arg;
|
||||||
|
else
|
||||||
|
hash = DEFAULT_HASH;
|
||||||
|
|
||||||
|
/* Create new device entry */
|
||||||
|
newdev = grub_malloc (sizeof (struct grub_crypto));
|
||||||
|
if (!newdev)
|
||||||
|
return grub_errno;
|
||||||
|
newdev->devname = grub_strdup (args[0]);
|
||||||
|
if (!newdev->devname)
|
||||||
|
{
|
||||||
|
grub_free (newdev);
|
||||||
|
return grub_errno;
|
||||||
|
}
|
||||||
|
newdev->source_devname = grub_strdup (args[1]);
|
||||||
|
if (!newdev->source_devname)
|
||||||
|
{
|
||||||
|
grub_free (newdev->devname);
|
||||||
|
grub_free (newdev);
|
||||||
|
return grub_errno;
|
||||||
|
}
|
||||||
|
newdev->has_partitions = state[1].set;
|
||||||
|
ciph = grub_crypto_lookup_cipher_by_name (cipher);
|
||||||
|
if (!ciph)
|
||||||
|
{
|
||||||
|
grub_free (newdev->source_devname);
|
||||||
|
grub_free (newdev->devname);
|
||||||
|
grub_free (newdev);
|
||||||
|
return grub_error (GRUB_ERR_CIPHER_NOT_FOUND, "Unknown cipher %s", hash);
|
||||||
|
}
|
||||||
|
newdev->cipher = grub_crypto_cipher_open (ciph);
|
||||||
|
if (!newdev->cipher)
|
||||||
|
{
|
||||||
|
grub_free (newdev->source_devname);
|
||||||
|
grub_free (newdev->devname);
|
||||||
|
grub_free (newdev);
|
||||||
|
return grub_errno;
|
||||||
|
}
|
||||||
|
hashparams = grub_crypto_lookup_md_by_name (hash);
|
||||||
|
if (!hashparams)
|
||||||
|
{
|
||||||
|
grub_free (newdev->source_devname);
|
||||||
|
grub_free (newdev->devname);
|
||||||
|
grub_free (newdev);
|
||||||
|
grub_crypto_cipher_close (newdev->cipher);
|
||||||
|
return grub_error (GRUB_ERR_CIPHER_NOT_FOUND, "Unknown digest %s", hash);
|
||||||
|
}
|
||||||
|
newdev->srcdisk = NULL;
|
||||||
|
if (state[5].set)
|
||||||
|
newdev->keysize = grub_strtoul (state[5].arg, NULL, 10);
|
||||||
|
else
|
||||||
|
newdev->keysize = 16;
|
||||||
|
|
||||||
|
/* Get passphrase */
|
||||||
|
if (state[4].set) /* Passphrase supplied on commandline */
|
||||||
|
passphrase = state[4].arg;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
#if 1
|
||||||
|
return 0;
|
||||||
|
#else
|
||||||
|
if (grub_strcmp (cipher, "none"))
|
||||||
|
{
|
||||||
|
grub_cmdline_get ("Passphrase: ", cmdphrase, MAX_PASSPHRASE, '*',
|
||||||
|
0);
|
||||||
|
passphrase = cmdphrase;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
err = set_passphrase (newdev, hashparams, passphrase);
|
||||||
|
if (err)
|
||||||
|
{
|
||||||
|
grub_crypto_cipher_close (newdev->cipher);
|
||||||
|
grub_free (newdev->source_devname);
|
||||||
|
grub_free (newdev->devname);
|
||||||
|
grub_free (newdev);
|
||||||
|
return err;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Add new entry to list and return */
|
||||||
|
newdev->next = crypto_list;
|
||||||
|
crypto_list = newdev;
|
||||||
|
|
||||||
|
/* Error conditions */
|
||||||
|
return GRUB_ERR_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/***** GRUB disk device interface ******************************************/
|
||||||
|
|
||||||
|
static int
|
||||||
|
grub_crypto_iterate (int (*hook) (const char *name))
|
||||||
|
{
|
||||||
|
grub_crypto_t i;
|
||||||
|
|
||||||
|
for (i = crypto_list; i != NULL; i = i->next)
|
||||||
|
if (hook (i->devname))
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static grub_err_t
|
||||||
|
grub_crypto_open (const char *name, grub_disk_t disk)
|
||||||
|
{
|
||||||
|
grub_crypto_t dev;
|
||||||
|
crypto_private_t private;
|
||||||
|
|
||||||
|
for (dev = crypto_list; dev != NULL; dev = dev->next)
|
||||||
|
if (grub_strcmp (dev->devname, name) == 0)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!dev)
|
||||||
|
return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "Can't open device");
|
||||||
|
|
||||||
|
/* Setup crypto private structure */
|
||||||
|
if (!(private = grub_malloc (sizeof (struct crypto_private))))
|
||||||
|
return grub_errno;
|
||||||
|
private->crypto = dev;
|
||||||
|
|
||||||
|
/* Open underlying device */
|
||||||
|
private->srcdisk = grub_disk_open (dev->source_devname);
|
||||||
|
if (!private->srcdisk)
|
||||||
|
{
|
||||||
|
return grub_errno;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Populate requested disk */
|
||||||
|
disk->total_sectors = grub_disk_get_size (private->srcdisk);
|
||||||
|
disk->id = (int) dev;
|
||||||
|
disk->has_partitions = dev->has_partitions;
|
||||||
|
disk->data = private;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
grub_crypto_close (grub_disk_t disk)
|
||||||
|
{
|
||||||
|
crypto_private_t private = (crypto_private_t) disk->data;
|
||||||
|
|
||||||
|
grub_disk_close (private->srcdisk);
|
||||||
|
grub_free (private);
|
||||||
|
}
|
||||||
|
|
||||||
|
static grub_err_t
|
||||||
|
grub_crypto_read (grub_disk_t disk, grub_disk_addr_t sector,
|
||||||
|
grub_size_t size, char *buf)
|
||||||
|
{
|
||||||
|
crypto_private_t private = (crypto_private_t) disk->data;
|
||||||
|
grub_err_t err;
|
||||||
|
grub_crypto_cipher_handle_t cipher = private->crypto->cipher;
|
||||||
|
grub_size_t i;
|
||||||
|
|
||||||
|
/* Read sectors from underlying disk */
|
||||||
|
err =
|
||||||
|
grub_disk_read (private->srcdisk, sector, 0,
|
||||||
|
size << GRUB_DISK_SECTOR_BITS, buf);
|
||||||
|
if (err)
|
||||||
|
return err;
|
||||||
|
|
||||||
|
/* Decrypt sectors */
|
||||||
|
for (i = 0; i < size; i++)
|
||||||
|
{
|
||||||
|
grub_disk_addr_t s = grub_cpu_to_le64 (sector + i);
|
||||||
|
grub_uint8_t iv[cipher->cipher->blocksize];
|
||||||
|
gcry_err_code_t gcry_err;
|
||||||
|
|
||||||
|
/* Set IV from raw sector number (plain mode) */
|
||||||
|
grub_memset (iv, 0, cipher->cipher->blocksize);
|
||||||
|
grub_memcpy (iv, &s,
|
||||||
|
MIN (sizeof (grub_disk_addr_t),
|
||||||
|
cipher->cipher->blocksize));
|
||||||
|
|
||||||
|
gcry_err = grub_crypto_cbc_decrypt (cipher,
|
||||||
|
buf + (i << GRUB_DISK_SECTOR_BITS),
|
||||||
|
buf + (i << GRUB_DISK_SECTOR_BITS),
|
||||||
|
GRUB_DISK_SECTOR_SIZE, iv);
|
||||||
|
if (gcry_err)
|
||||||
|
return grub_crypto_gcry_error (gcry_err);
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static grub_err_t
|
||||||
|
grub_crypto_write (grub_disk_t disk __attribute ((unused)),
|
||||||
|
grub_disk_addr_t sector __attribute ((unused)),
|
||||||
|
grub_size_t size __attribute ((unused)),
|
||||||
|
const char *buf __attribute ((unused)))
|
||||||
|
{
|
||||||
|
return GRUB_ERR_NOT_IMPLEMENTED_YET;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct grub_disk_dev grub_crypto_dev = {
|
||||||
|
.name = "crypto",
|
||||||
|
.id = GRUB_DISK_DEVICE_DEVMAP_ID,
|
||||||
|
.iterate = grub_crypto_iterate,
|
||||||
|
.open = grub_crypto_open,
|
||||||
|
.close = grub_crypto_close,
|
||||||
|
.read = grub_crypto_read,
|
||||||
|
.write = grub_crypto_write,
|
||||||
|
.next = 0
|
||||||
|
};
|
||||||
|
|
||||||
|
/***** GRUB module (de-)initialization *************************************/
|
||||||
|
|
||||||
|
static grub_extcmd_t cmd;
|
||||||
|
|
||||||
|
GRUB_MOD_INIT (devmapper)
|
||||||
|
{
|
||||||
|
cmd = grub_register_extcmd ("devmap", grub_cmd_devmap, GRUB_COMMAND_FLAG_BOTH,
|
||||||
|
"devmap [OPTIONS...] [DEVICE] [SRC-DEV]",
|
||||||
|
"Map one device onto another (w/ cryptography support).",
|
||||||
|
options);
|
||||||
|
grub_disk_dev_register (&grub_crypto_dev);
|
||||||
|
}
|
||||||
|
|
||||||
|
GRUB_MOD_FINI (devmapper)
|
||||||
|
{
|
||||||
|
grub_unregister_extcmd (cmd);
|
||||||
|
grub_disk_dev_unregister (&grub_crypto_dev);
|
||||||
|
}
|
||||||
@@ -18,10 +18,42 @@
|
|||||||
|
|
||||||
#include <grub/efiemu/efiemu.h>
|
#include <grub/efiemu/efiemu.h>
|
||||||
#include <grub/command.h>
|
#include <grub/command.h>
|
||||||
#include <grub/i386/cpuid.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)
|
||||||
|
|
||||||
const char *
|
const char *
|
||||||
grub_efiemu_get_default_core_name (void)
|
grub_efiemu_get_default_core_name (void)
|
||||||
{
|
{
|
||||||
return grub_cpuid_has_longmode ? "efiemu64.o" : "efiemu32.o";
|
|
||||||
|
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";
|
||||||
}
|
}
|
||||||
@@ -24,7 +24,6 @@
|
|||||||
#include <grub/time.h>
|
#include <grub/time.h>
|
||||||
#include <grub/misc.h>
|
#include <grub/misc.h>
|
||||||
#include <grub/i386/tsc.h>
|
#include <grub/i386/tsc.h>
|
||||||
#include <grub/i386/cpuid.h>
|
|
||||||
#include <grub/i386/pit.h>
|
#include <grub/i386/pit.h>
|
||||||
#include <grub/cpu/io.h>
|
#include <grub/cpu/io.h>
|
||||||
|
|
||||||
@@ -36,35 +35,6 @@ static grub_uint64_t tsc_boot_time;
|
|||||||
in 32-bit. */
|
in 32-bit. */
|
||||||
grub_uint32_t grub_tsc_rate;
|
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
|
static void
|
||||||
grub_pit_wait (grub_uint16_t tics)
|
grub_pit_wait (grub_uint16_t tics)
|
||||||
{
|
{
|
||||||
@@ -93,7 +63,7 @@ grub_pit_wait (grub_uint16_t tics)
|
|||||||
GRUB_PIT_SPEAKER_PORT);
|
GRUB_PIT_SPEAKER_PORT);
|
||||||
}
|
}
|
||||||
|
|
||||||
static grub_uint64_t
|
grub_uint64_t
|
||||||
grub_tsc_get_time_ms (void)
|
grub_tsc_get_time_ms (void)
|
||||||
{
|
{
|
||||||
grub_uint64_t a = grub_get_tsc () - tsc_boot_time;
|
grub_uint64_t a = grub_get_tsc () - tsc_boot_time;
|
||||||
|
|||||||
@@ -25,7 +25,6 @@
|
|||||||
#include <grub/loader.h>
|
#include <grub/loader.h>
|
||||||
#include <grub/autoefi.h>
|
#include <grub/autoefi.h>
|
||||||
#include <grub/i386/tsc.h>
|
#include <grub/i386/tsc.h>
|
||||||
#include <grub/i386/cpuid.h>
|
|
||||||
#include <grub/efi/api.h>
|
#include <grub/efi/api.h>
|
||||||
#include <grub/i386/pit.h>
|
#include <grub/i386/pit.h>
|
||||||
#include <grub/misc.h>
|
#include <grub/misc.h>
|
||||||
@@ -126,22 +125,66 @@ guessfsb (void)
|
|||||||
{
|
{
|
||||||
const grub_uint64_t sane_value = 100000000;
|
const grub_uint64_t sane_value = 100000000;
|
||||||
grub_uint32_t manufacturer[3], max_cpuid, capabilities, msrlow;
|
grub_uint32_t manufacturer[3], max_cpuid, capabilities, msrlow;
|
||||||
grub_uint32_t a, b, d;
|
|
||||||
|
|
||||||
if (! grub_cpu_is_cpuid_supported ())
|
if (! grub_cpu_is_cpuid_supported ())
|
||||||
return sane_value;
|
return sane_value;
|
||||||
|
|
||||||
grub_cpuid (0, max_cpuid, manufacturer[0], manufacturer[2], manufacturer[1]);
|
#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]));
|
||||||
|
|
||||||
/* Only Intel for now is done. */
|
/* Only Intel for now is done. */
|
||||||
if (grub_memcmp (manufacturer, "GenuineIntel", 12) != 0)
|
if (grub_memcmp (manufacturer, "GenuineIntel", 12) != 0)
|
||||||
return sane_value;
|
return sane_value;
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Check Speedstep. */
|
/* Check Speedstep. */
|
||||||
if (max_cpuid < 1)
|
if (max_cpuid < 1)
|
||||||
return sane_value;
|
return sane_value;
|
||||||
|
|
||||||
grub_cpuid (1, a, b, capabilities, d);
|
#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
|
||||||
|
|
||||||
if (! (capabilities & (1 << 7)))
|
if (! (capabilities & (1 << 7)))
|
||||||
return sane_value;
|
return sane_value;
|
||||||
|
|||||||
@@ -1,106 +0,0 @@
|
|||||||
/*
|
|
||||||
* GRUB -- GRand Unified Bootloader
|
|
||||||
* Copyright (C) 2012 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/partition.h>
|
|
||||||
#include <grub/disk.h>
|
|
||||||
#include <grub/mm.h>
|
|
||||||
#include <grub/misc.h>
|
|
||||||
#include <grub/dl.h>
|
|
||||||
#include <grub/symbol.h>
|
|
||||||
#include <grub/types.h>
|
|
||||||
#include <grub/err.h>
|
|
||||||
|
|
||||||
GRUB_MOD_LICENSE ("GPLv3+");
|
|
||||||
|
|
||||||
static struct grub_partition_map grub_dasd_partition_map;
|
|
||||||
|
|
||||||
struct addr
|
|
||||||
{
|
|
||||||
grub_uint16_t cyl;
|
|
||||||
grub_uint16_t head;
|
|
||||||
grub_uint8_t sec;
|
|
||||||
} __attribute__ ((packed));
|
|
||||||
|
|
||||||
struct anchor
|
|
||||||
{
|
|
||||||
grub_uint8_t unused1[4];
|
|
||||||
grub_uint8_t magic[4];
|
|
||||||
grub_uint8_t unused2[7];
|
|
||||||
struct addr vtoc_addr;
|
|
||||||
} __attribute__ ((packed));
|
|
||||||
|
|
||||||
/* VOL1 in EBCDIC. */
|
|
||||||
#define ANCHOR_MAGIC "\xe5\xd6\xd3\xf1"
|
|
||||||
|
|
||||||
struct grub_disk_addr_t
|
|
||||||
address_to_block (const struct addr *a)
|
|
||||||
{
|
|
||||||
return a->cyl * + a->head * + a->sec;
|
|
||||||
}
|
|
||||||
|
|
||||||
static grub_err_t
|
|
||||||
dasd_partition_map_iterate (grub_disk_t disk,
|
|
||||||
int (*hook) (grub_disk_t disk,
|
|
||||||
const grub_partition_t partition))
|
|
||||||
{
|
|
||||||
grub_err_t err;
|
|
||||||
grub_partition_t p;
|
|
||||||
struct anchor anchor;
|
|
||||||
|
|
||||||
err = grub_disk_read (disk, 2 * 8, 0, sizeof (anchor), &anchor);
|
|
||||||
if (err)
|
|
||||||
return err;
|
|
||||||
if (grub_memcmp (anchor.magic, ANCHOR_MAGIC, sizeof (ANCHOR_MAGIC) - 1) != 0)
|
|
||||||
return grub_error (GRUB_ERR_BAD_PART_TABLE,
|
|
||||||
"not a dasd partition table");
|
|
||||||
|
|
||||||
p = (grub_partition_t) grub_zalloc (sizeof (struct grub_partition));
|
|
||||||
if (! p)
|
|
||||||
return grub_errno;
|
|
||||||
p->partmap = &grub_dasd_partition_map;
|
|
||||||
|
|
||||||
p->start = 0x18 << 3;
|
|
||||||
p->len = disk->total_sectors - p->start;
|
|
||||||
p->number = 0;
|
|
||||||
if (hook (disk, p))
|
|
||||||
{
|
|
||||||
grub_free (p);
|
|
||||||
return GRUB_ERR_NONE;
|
|
||||||
}
|
|
||||||
|
|
||||||
grub_free (p);
|
|
||||||
return GRUB_ERR_NONE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Partition map type. */
|
|
||||||
static struct grub_partition_map grub_dasd_partition_map =
|
|
||||||
{
|
|
||||||
.name = "dasd",
|
|
||||||
.iterate = dasd_partition_map_iterate,
|
|
||||||
};
|
|
||||||
|
|
||||||
GRUB_MOD_INIT(part_dasd)
|
|
||||||
{
|
|
||||||
grub_partition_map_register (&grub_dasd_partition_map);
|
|
||||||
}
|
|
||||||
|
|
||||||
GRUB_MOD_FINI(part_dasd)
|
|
||||||
{
|
|
||||||
grub_partition_map_unregister (&grub_dasd_partition_map);
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -29,7 +29,7 @@
|
|||||||
#include <grub/video.h>
|
#include <grub/video.h>
|
||||||
#include <grub/i386/pc/int.h>
|
#include <grub/i386/pc/int.h>
|
||||||
#include <grub/i18n.h>
|
#include <grub/i18n.h>
|
||||||
#include <grub/cpu/cpuid.h>
|
#include <grub/cpu/tsc.h>
|
||||||
|
|
||||||
GRUB_MOD_LICENSE ("GPLv3+");
|
GRUB_MOD_LICENSE ("GPLv3+");
|
||||||
|
|
||||||
@@ -58,6 +58,11 @@ real2pm (grub_vbe_farptr_t ptr)
|
|||||||
+ ((unsigned long) ptr & 0x0000FFFF));
|
+ ((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) \
|
#define rdmsr(num,a,d) \
|
||||||
asm volatile ("rdmsr" : "=a" (a), "=d" (d) : "c" (num))
|
asm volatile ("rdmsr" : "=a" (a), "=d" (d) : "c" (num))
|
||||||
|
|
||||||
@@ -131,7 +136,7 @@ grub_vbe_enable_mtrr (grub_uint8_t *base, grub_size_t size)
|
|||||||
if (! grub_cpu_is_cpuid_supported ())
|
if (! grub_cpu_is_cpuid_supported ())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
grub_cpuid (1, eax, ebx, ecx, edx);
|
cpuid (1, eax, ebx, ecx, edx);
|
||||||
features = edx;
|
features = edx;
|
||||||
if (! (features & 0x00001000)) /* MTRR */
|
if (! (features & 0x00001000)) /* MTRR */
|
||||||
return;
|
return;
|
||||||
@@ -142,11 +147,11 @@ grub_vbe_enable_mtrr (grub_uint8_t *base, grub_size_t size)
|
|||||||
return;
|
return;
|
||||||
var_mtrrs = (mtrrcap & 0xFF);
|
var_mtrrs = (mtrrcap & 0xFF);
|
||||||
|
|
||||||
grub_cpuid (0x80000000, eax, ebx, ecx, edx);
|
cpuid (0x80000000, eax, ebx, ecx, edx);
|
||||||
max_extended_cpuid = eax;
|
max_extended_cpuid = eax;
|
||||||
if (max_extended_cpuid >= 0x80000008)
|
if (max_extended_cpuid >= 0x80000008)
|
||||||
{
|
{
|
||||||
grub_cpuid (0x80000008, eax, ebx, ecx, edx);
|
cpuid (0x80000008, eax, ebx, ecx, edx);
|
||||||
maxphyaddr = (eax & 0xFF);
|
maxphyaddr = (eax & 0xFF);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -48,6 +48,7 @@ enum grub_disk_dev_id
|
|||||||
GRUB_DISK_DEVICE_PROCFS_ID,
|
GRUB_DISK_DEVICE_PROCFS_ID,
|
||||||
GRUB_DISK_DEVICE_CBFSDISK_ID,
|
GRUB_DISK_DEVICE_CBFSDISK_ID,
|
||||||
GRUB_DISK_DEVICE_UBOOTDISK_ID,
|
GRUB_DISK_DEVICE_UBOOTDISK_ID,
|
||||||
|
GRUB_DISK_DEVICE_DEVMAP_ID
|
||||||
};
|
};
|
||||||
|
|
||||||
struct grub_disk;
|
struct grub_disk;
|
||||||
|
|||||||
@@ -21,64 +21,4 @@
|
|||||||
|
|
||||||
extern unsigned char grub_cpuid_has_longmode;
|
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
|
#endif
|
||||||
@@ -21,7 +21,122 @@
|
|||||||
|
|
||||||
#include <grub/types.h>
|
#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);
|
void grub_tsc_init (void);
|
||||||
|
grub_uint64_t grub_tsc_get_time_ms (void);
|
||||||
/* In ms per 2^32 ticks. */
|
/* In ms per 2^32 ticks. */
|
||||||
extern grub_uint32_t EXPORT_VAR(grub_tsc_rate);
|
extern grub_uint32_t EXPORT_VAR(grub_tsc_rate);
|
||||||
|
|
||||||
|
|||||||
@@ -65,7 +65,7 @@ argument () {
|
|||||||
shift
|
shift
|
||||||
|
|
||||||
if test $# -eq 0; then
|
if test $# -eq 0; then
|
||||||
gettext_printf "%s: option requires an argument -- \`%s'\n" "$self" "$opt" 1>&2
|
gettext_printf "%s: option requires an argument -- \`%s'\n" "$0" "$opt" 1>&2
|
||||||
exit 1
|
exit 1
|
||||||
fi
|
fi
|
||||||
echo $1
|
echo $1
|
||||||
|
|||||||
+1
-1
@@ -65,7 +65,7 @@ argument () {
|
|||||||
shift
|
shift
|
||||||
|
|
||||||
if test $# -eq 0; then
|
if test $# -eq 0; then
|
||||||
gettext_printf "%s: option requires an argument -- \`%s'\n" "$self" "$opt" 1>&2
|
gettext_printf "%s: option requires an argument -- \`%s'\n" "$0" "$opt" 1>&2
|
||||||
exit 1
|
exit 1
|
||||||
fi
|
fi
|
||||||
echo $1
|
echo $1
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ argument () {
|
|||||||
shift
|
shift
|
||||||
|
|
||||||
if test $# -eq 0; then
|
if test $# -eq 0; then
|
||||||
gettext_printf "%s: option requires an argument -- \`%s'\n" "$self" "$opt" 1>&2
|
gettext_printf "%s: option requires an argument -- \`%s'\n" "$0" "$opt" 1>&2
|
||||||
exit 1
|
exit 1
|
||||||
fi
|
fi
|
||||||
echo $1
|
echo $1
|
||||||
|
|||||||
@@ -191,7 +191,7 @@ EOF
|
|||||||
EOF
|
EOF
|
||||||
|
|
||||||
# Gettext variables and module
|
# Gettext variables and module
|
||||||
if [ "x${LANG}" != "xC" ] && [ "x${LANG}" != "x" ]; then
|
if [ "x${LANG}" != "xC" ] ; then
|
||||||
cat << EOF
|
cat << EOF
|
||||||
set locale_dir=\$prefix/locale
|
set locale_dir=\$prefix/locale
|
||||||
set lang=${grub_lang}
|
set lang=${grub_lang}
|
||||||
|
|||||||
Reference in new issue
Block a user