Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to allocate an executable page in a Linux kernel module?

I'm writing a Linux kernel module, and I'd like to allocate an executable page. Plain kmalloc() returns a pointer within a non-executable page, and I get a kernel panic when executing code there. It has to work on Ubuntu Karmic x86, 2.6.31-20-generic-pae.

like image 879
pts Avatar asked Mar 16 '10 23:03

pts


People also ask

How does Linux kernel allocate memory?

Linux-based operating systems use a virtual memory system. Any address referenced by a user-space application must be translated into a physical address. This is achieved through a combination of page tables and address translation hardware in the underlying computer system.

Which is the correct way to allocate limited memory inside the module?

If a module needs to allocate big chunks of memory, it is usually better to use a page-oriented technique. Requesting whole pages also has other advantages, which are introduced in Chapter 15.

How does Linux load an executable?

The executable is invoked by filename with execve(). The kernel loads the executable into the process, and looks for a PT_INTERP entry in its ELF Program Headers; this specifies the filename of the dynamic linker (/lib/ld-linux. so. 2 for glibc on Linux).


2 Answers

#include <linux/vmalloc.h>
#include <asm/pgtype_types.h>
...
char *p = __vmalloc(byte_size, GFP_KERNEL, PAGE_KERNEL_EXEC);
...
if (p != NULL) vfree(p);
like image 119
pts Avatar answered Sep 19 '22 13:09

pts


/**
 * vmalloc_exec - allocate virtually contiguous, executable memory
 * @size:     allocation size
 *
 * Kernel-internal function to allocate enough pages to cover @size
 * the page level allocator and map them into contiguous and
 * executable kernel virtual space.
 *
 * For tight control over page level allocator and protection flags
 * use __vmalloc() instead.
 *
 * Return: pointer to the allocated memory or %NULL on error
 */
void *vmalloc_exec(unsigned long size)
{
    return __vmalloc_node(size, 1, GFP_KERNEL, PAGE_KERNEL_EXEC,
                  NUMA_NO_NODE, __builtin_return_address(0));
}
like image 33
youfu Avatar answered Sep 20 '22 13:09

youfu