Move OS-dependent mprotect for module loading to grub-core/osdep/*/dl.c
and implement windows variant.
This commit is contained in:
parent
d5c14e1e26
commit
a19293cb75
7 changed files with 147 additions and 13 deletions
|
@ -1,3 +1,8 @@
|
||||||
|
2013-12-08 Vladimir Serbinenko <phcoder@gmail.com>
|
||||||
|
|
||||||
|
Move OS-dependent mprotect for module loading to grub-core/osdep/*/dl.c
|
||||||
|
and implement windows variant.
|
||||||
|
|
||||||
2013-12-08 Vladimir Serbinenko <phcoder@gmail.com>
|
2013-12-08 Vladimir Serbinenko <phcoder@gmail.com>
|
||||||
|
|
||||||
Fix mips-emu compilation.
|
Fix mips-emu compilation.
|
||||||
|
|
|
@ -282,6 +282,9 @@ kernel = {
|
||||||
emu = osdep/emuconsole.c;
|
emu = osdep/emuconsole.c;
|
||||||
extra_dist = osdep/unix/emuconsole.c;
|
extra_dist = osdep/unix/emuconsole.c;
|
||||||
extra_dist = osdep/windows/emuconsole.c;
|
extra_dist = osdep/windows/emuconsole.c;
|
||||||
|
emu = osdep/dl.c;
|
||||||
|
extra_dist = osdep/unix/dl.c;
|
||||||
|
extra_dist = osdep/windows/dl.c;
|
||||||
emu = osdep/sleep.c;
|
emu = osdep/sleep.c;
|
||||||
emu = osdep/init.c;
|
emu = osdep/init.c;
|
||||||
emu = osdep/emunet.c;
|
emu = osdep/emunet.c;
|
||||||
|
|
|
@ -38,10 +38,6 @@
|
||||||
#define GRUB_MODULES_MACHINE_READONLY
|
#define GRUB_MODULES_MACHINE_READONLY
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef GRUB_MACHINE_EMU
|
|
||||||
#include <sys/mman.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#pragma GCC diagnostic ignored "-Wcast-align"
|
#pragma GCC diagnostic ignored "-Wcast-align"
|
||||||
|
@ -258,21 +254,15 @@ grub_dl_load_segments (grub_dl_t mod, const Elf_Ehdr *e)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef GRUB_MACHINE_EMU
|
#ifdef GRUB_MACHINE_EMU
|
||||||
if (talign < 8192 * 16)
|
mod->base = grub_osdep_dl_memalign (talign, tsize);
|
||||||
talign = 8192 * 16;
|
#else
|
||||||
tsize = ALIGN_UP (tsize, 8192 * 16);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
mod->base = grub_memalign (talign, tsize);
|
mod->base = grub_memalign (talign, tsize);
|
||||||
|
#endif
|
||||||
if (!mod->base)
|
if (!mod->base)
|
||||||
return grub_errno;
|
return grub_errno;
|
||||||
mod->sz = tsize;
|
mod->sz = tsize;
|
||||||
ptr = mod->base;
|
ptr = mod->base;
|
||||||
|
|
||||||
#ifdef GRUB_MACHINE_EMU
|
|
||||||
mprotect (mod->base, tsize, PROT_READ | PROT_WRITE | PROT_EXEC);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
for (i = 0, s = (Elf_Shdr *)((char *) e + e->e_shoff);
|
for (i = 0, s = (Elf_Shdr *)((char *) e + e->e_shoff);
|
||||||
i < e->e_shnum;
|
i < e->e_shnum;
|
||||||
i++, s = (Elf_Shdr *)((char *) s + e->e_shentsize))
|
i++, s = (Elf_Shdr *)((char *) s + e->e_shentsize))
|
||||||
|
@ -782,7 +772,11 @@ grub_dl_unload (grub_dl_t mod)
|
||||||
grub_free (dep);
|
grub_free (dep);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef GRUB_MACHINE_EMU
|
||||||
|
grub_dl_osdep_dl_free (mod->base);
|
||||||
|
#else
|
||||||
grub_free (mod->base);
|
grub_free (mod->base);
|
||||||
|
#endif
|
||||||
grub_free (mod->name);
|
grub_free (mod->name);
|
||||||
#ifdef GRUB_MODULES_MACHINE_READONLY
|
#ifdef GRUB_MODULES_MACHINE_READONLY
|
||||||
grub_free (mod->symtab);
|
grub_free (mod->symtab);
|
||||||
|
|
5
grub-core/osdep/dl.c
Normal file
5
grub-core/osdep/dl.c
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
#if defined (__MINGW32__) || defined (__CYGWIN__)
|
||||||
|
#include "windows/dl.c"
|
||||||
|
#else
|
||||||
|
#include "unix/dl.c"
|
||||||
|
#endif
|
61
grub-core/osdep/unix/dl.c
Normal file
61
grub-core/osdep/unix/dl.c
Normal file
|
@ -0,0 +1,61 @@
|
||||||
|
/*
|
||||||
|
* GRUB -- GRand Unified Bootloader
|
||||||
|
* Copyright (C) 2013 Free Software Foundation, Inc.
|
||||||
|
*
|
||||||
|
* GRUB is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* GRUB is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <config.h>
|
||||||
|
#include <config-util.h>
|
||||||
|
|
||||||
|
#include <grub/dl.h>
|
||||||
|
#include <grub/misc.h>
|
||||||
|
#include <grub/mm.h>
|
||||||
|
#include <sys/mman.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
void *
|
||||||
|
grub_osdep_dl_memalign (grub_size_t align, grub_size_t size)
|
||||||
|
{
|
||||||
|
void *ret;
|
||||||
|
if (align < 8192 * 16)
|
||||||
|
align = 8192 * 16;
|
||||||
|
size = ALIGN_UP (size, 8192 * 16);
|
||||||
|
|
||||||
|
#if defined(HAVE_POSIX_MEMALIGN)
|
||||||
|
if (posix_memalign (&ret, align, size) != 0)
|
||||||
|
ret = 0;
|
||||||
|
#elif defined(HAVE_MEMALIGN)
|
||||||
|
ret = memalign (align, size);
|
||||||
|
#else
|
||||||
|
#error "Complete this"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (!ret)
|
||||||
|
{
|
||||||
|
grub_error (GRUB_ERR_OUT_OF_MEMORY, N_("out of memory"));
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
mprotect (ret, size, PROT_READ | PROT_WRITE | PROT_EXEC);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
grub_dl_osdep_dl_free (void *ptr)
|
||||||
|
{
|
||||||
|
if (ptr)
|
||||||
|
free (ptr);
|
||||||
|
}
|
59
grub-core/osdep/windows/dl.c
Normal file
59
grub-core/osdep/windows/dl.c
Normal file
|
@ -0,0 +1,59 @@
|
||||||
|
/*
|
||||||
|
* GRUB -- GRand Unified Bootloader
|
||||||
|
* Copyright (C) 2013 Free Software Foundation, Inc.
|
||||||
|
*
|
||||||
|
* GRUB is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* GRUB is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with GRUB. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <config.h>
|
||||||
|
#include <config-util.h>
|
||||||
|
|
||||||
|
#include <grub/dl.h>
|
||||||
|
#include <grub/misc.h>
|
||||||
|
#include <grub/mm.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <windows.h>
|
||||||
|
|
||||||
|
void *
|
||||||
|
grub_osdep_dl_memalign (grub_size_t align, grub_size_t size)
|
||||||
|
{
|
||||||
|
void *ret;
|
||||||
|
if (align > 4096)
|
||||||
|
{
|
||||||
|
grub_error (GRUB_ERR_NOT_IMPLEMENTED_YET, N_("too large alignment"));
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
size = ALIGN_UP (size, 4096);
|
||||||
|
|
||||||
|
ret = VirtualAlloc (NULL, size, MEM_COMMIT | MEM_RESERVE,
|
||||||
|
PAGE_EXECUTE_READWRITE);
|
||||||
|
|
||||||
|
if (!ret)
|
||||||
|
{
|
||||||
|
grub_error (GRUB_ERR_OUT_OF_MEMORY, N_("out of memory"));
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
grub_dl_osdep_dl_free (void *ptr)
|
||||||
|
{
|
||||||
|
if (!ptr)
|
||||||
|
return;
|
||||||
|
VirtualFree (ptr, 0, MEM_RELEASE);
|
||||||
|
}
|
|
@ -210,6 +210,13 @@ extern grub_dl_t EXPORT_VAR(grub_dl_head);
|
||||||
|
|
||||||
#define FOR_DL_MODULES(var) FOR_LIST_ELEMENTS ((var), (grub_dl_head))
|
#define FOR_DL_MODULES(var) FOR_LIST_ELEMENTS ((var), (grub_dl_head))
|
||||||
|
|
||||||
|
#ifdef GRUB_MACHINE_EMU
|
||||||
|
void *
|
||||||
|
grub_osdep_dl_memalign (grub_size_t align, grub_size_t size);
|
||||||
|
void
|
||||||
|
grub_dl_osdep_dl_free (void *ptr);
|
||||||
|
#endif
|
||||||
|
|
||||||
static inline void
|
static inline void
|
||||||
grub_dl_init (grub_dl_t mod)
|
grub_dl_init (grub_dl_t mod)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue