mirror of
https://github.com/genodelabs/genode.git
synced 2025-06-17 22:58:26 +00:00
base: hide internals of the Thread API
This patch moves details about the stack allocation and organization the base-internal headers. Thereby, I replaced the notion of "thread contexts" by "stacks" as this term is much more intuitive. The fact that we place thread-specific information at the bottom of the stack is not worth introducing new terminology. Issue #1832
This commit is contained in:
committed by
Christian Helmuth
parent
3c686fc9c6
commit
7f73e5e879
20
repos/base-linux/src/base/env/rm_session_mmap.cc
vendored
20
repos/base-linux/src/base/env/rm_session_mmap.cc
vendored
@ -8,7 +8,7 @@
|
||||
* dataspaces and 2) get the kernel to manage VM regions as we intent.
|
||||
*
|
||||
* The kernel sets up mappings for the binary on execve(), which are text and
|
||||
* data segments, the context area and special regions (stack, vdso, vsyscall).
|
||||
* data segments, the stack area and special regions (stack, vdso, vsyscall).
|
||||
* Later mappings are done by the Genode program itself, which knows nothing
|
||||
* about these initial mappings. Therefore, most mmap() operations are _soft_
|
||||
* to detect region conflicts with existing mappings or let the kernel find
|
||||
@ -17,10 +17,10 @@
|
||||
* but not populated dataspaces are "holes" in the Linux VM space represented
|
||||
* by PROT_NONE mappings (see _reserve_local()).
|
||||
*
|
||||
* The context area is a managed dataspace as on other platforms, which is
|
||||
* The stack area is a managed dataspace as on other platforms, which is
|
||||
* created and attached during program launch. The managed dataspace replaces
|
||||
* the inital reserved area, which is therefore flushed beforehand. Hybrid
|
||||
* programs have no context area.
|
||||
* programs have no stack area.
|
||||
*
|
||||
* Note, we do not support nesting of managed dataspaces.
|
||||
*/
|
||||
@ -40,7 +40,7 @@
|
||||
/* base-internal includes */
|
||||
#include <base/internal/local_capability.h>
|
||||
#include <base/internal/platform_env.h>
|
||||
#include <base/internal/context_area.h>
|
||||
#include <base/internal/stack_area.h>
|
||||
|
||||
using namespace Genode;
|
||||
|
||||
@ -58,13 +58,13 @@ addr_t Platform_env_base::Rm_session_mmap::_reserve_local(bool use_loc
|
||||
addr_t local_addr,
|
||||
Genode::size_t size)
|
||||
{
|
||||
/* special handling for context area */
|
||||
/* special handling for stack area */
|
||||
if (use_local_addr
|
||||
&& local_addr == Native_config::context_area_virtual_base()
|
||||
&& size == Native_config::context_area_virtual_size()) {
|
||||
&& local_addr == Native_config::stack_area_virtual_base()
|
||||
&& size == Native_config::stack_area_virtual_size()) {
|
||||
|
||||
/*
|
||||
* On the first request to reserve the context area, we flush the
|
||||
* On the first request to reserve the stack area, we flush the
|
||||
* initial mapping preserved in linker script and apply the actual
|
||||
* reservation. Subsequent requests are just ignored.
|
||||
*/
|
||||
@ -73,8 +73,8 @@ addr_t Platform_env_base::Rm_session_mmap::_reserve_local(bool use_loc
|
||||
{
|
||||
Context()
|
||||
{
|
||||
flush_context_area();
|
||||
reserve_context_area();
|
||||
flush_stack_area();
|
||||
reserve_stack_area();
|
||||
}
|
||||
} inst;
|
||||
|
||||
|
@ -19,6 +19,9 @@
|
||||
#include <base/sleep.h>
|
||||
#include <linux_cpu_session/linux_cpu_session.h>
|
||||
|
||||
/* base-internal includes */
|
||||
#include <base/internal/stack.h>
|
||||
|
||||
/* Linux syscall bindings */
|
||||
#include <linux_syscalls.h>
|
||||
|
||||
@ -77,7 +80,7 @@ void Thread_base::_init_platform_thread(size_t weight, Type type)
|
||||
|
||||
/* for normal threads create an object at the CPU session */
|
||||
if (type == NORMAL) {
|
||||
_thread_cap = _cpu_session->create_thread(weight, _context->name);
|
||||
_thread_cap = _cpu_session->create_thread(weight, _stack->name().string());
|
||||
return;
|
||||
}
|
||||
/* adjust initial object state for main threads */
|
||||
|
@ -28,7 +28,6 @@
|
||||
/* base-internal includes */
|
||||
#include <base/internal/platform_env.h>
|
||||
|
||||
|
||||
namespace Genode {
|
||||
|
||||
/**
|
||||
|
@ -18,29 +18,29 @@
|
||||
#include <base/thread.h>
|
||||
|
||||
/* base-internal includes */
|
||||
#include <base/internal/context_area.h>
|
||||
#include <base/internal/stack_area.h>
|
||||
|
||||
|
||||
/**
|
||||
* Region-manager session for allocating thread contexts
|
||||
* Region-manager session for allocating stacks
|
||||
*
|
||||
* This class corresponds to the managed dataspace that is normally
|
||||
* used for organizing thread contexts with the thread context area.
|
||||
* It "emulates" the sub address space by adjusting the local address
|
||||
* argument to 'attach' with the offset of the thread context area.
|
||||
* This class corresponds to the managed dataspace that is normally used for
|
||||
* organizing stacks within the stack. It "emulates" the sub address space by
|
||||
* adjusting the local address argument to 'attach' with the offset of the
|
||||
* stack area.
|
||||
*/
|
||||
class Context_area_rm_session : public Genode::Rm_session
|
||||
class Stack_area_rm_session : public Genode::Rm_session
|
||||
{
|
||||
public:
|
||||
|
||||
Context_area_rm_session()
|
||||
Stack_area_rm_session()
|
||||
{
|
||||
flush_context_area();
|
||||
reserve_context_area();
|
||||
flush_stack_area();
|
||||
reserve_stack_area();
|
||||
}
|
||||
|
||||
/**
|
||||
* Attach backing store to thread-context area
|
||||
* Attach backing store to stack area
|
||||
*/
|
||||
Local_addr attach(Genode::Dataspace_capability ds_cap,
|
||||
Genode::size_t size, Genode::off_t offset,
|
||||
@ -49,9 +49,9 @@ class Context_area_rm_session : public Genode::Rm_session
|
||||
{
|
||||
using namespace Genode;
|
||||
|
||||
/* convert context-area-relative to absolute virtual address */
|
||||
/* convert stack-area-relative to absolute virtual address */
|
||||
addr_t addr = local_addr;
|
||||
addr += Native_config::context_area_virtual_base();
|
||||
addr += Native_config::stack_area_virtual_base();
|
||||
|
||||
/* use anonymous mmap for allocating stack backing store */
|
||||
int flags = MAP_FIXED | MAP_ANONYMOUS | MAP_PRIVATE;
|
||||
@ -65,7 +65,7 @@ class Context_area_rm_session : public Genode::Rm_session
|
||||
}
|
||||
|
||||
void detach(Local_addr local_addr) {
|
||||
PWRN("context area detach from 0x%p - not implemented", (void *)local_addr); }
|
||||
PWRN("stack area detach from 0x%p - not implemented", (void *)local_addr); }
|
||||
|
||||
Genode::Pager_capability add_client(Genode::Thread_capability) {
|
||||
return Genode::Pager_capability(); }
|
||||
@ -81,7 +81,7 @@ class Context_area_rm_session : public Genode::Rm_session
|
||||
};
|
||||
|
||||
|
||||
class Context_area_ram_session : public Genode::Ram_session
|
||||
class Stack_area_ram_session : public Genode::Ram_session
|
||||
{
|
||||
public:
|
||||
|
||||
@ -102,19 +102,19 @@ class Context_area_ram_session : public Genode::Ram_session
|
||||
|
||||
|
||||
/**
|
||||
* Return single instance of the context-area RM and RAM session
|
||||
* Return single instance of the stack-area RM and RAM session
|
||||
*/
|
||||
namespace Genode {
|
||||
|
||||
Rm_session *env_context_area_rm_session()
|
||||
Rm_session *env_stack_area_rm_session()
|
||||
{
|
||||
static Context_area_rm_session inst;
|
||||
static Stack_area_rm_session inst;
|
||||
return &inst;
|
||||
}
|
||||
|
||||
Ram_session *env_context_area_ram_session()
|
||||
Ram_session *env_stack_area_ram_session()
|
||||
{
|
||||
static Context_area_ram_session inst;
|
||||
static Stack_area_ram_session inst;
|
||||
return &inst;
|
||||
}
|
||||
}
|
@ -24,7 +24,7 @@ SRC_CC = main.cc \
|
||||
signal_source_component.cc \
|
||||
trace_session_component.cc \
|
||||
thread_linux.cc \
|
||||
context_area.cc \
|
||||
stack_area.cc \
|
||||
core_printf.cc \
|
||||
thread.cc myself.cc
|
||||
|
||||
|
@ -211,7 +211,7 @@ namespace Genode {
|
||||
* the common use case of managed dataspaces as mechanism
|
||||
* to reserve parts of the local address space from being
|
||||
* populated by the 'env()->rm_session()'. (i.e., for the
|
||||
* context area, or for the placement of consecutive
|
||||
* stack area, or for the placement of consecutive
|
||||
* shared-library segments)
|
||||
*/
|
||||
addr_t _base;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* \brief Linux-specific utilities for context area
|
||||
* \brief Linux-specific utilities for stack area
|
||||
* \author Christian Helmuth
|
||||
* \date 2013-09-26
|
||||
*/
|
||||
@ -11,8 +11,8 @@
|
||||
* under the terms of the GNU General Public License version 2.
|
||||
*/
|
||||
|
||||
#ifndef _INCLUDE__BASE__INTERNAL__CONTEXT_AREA_H_
|
||||
#define _INCLUDE__BASE__INTERNAL__CONTEXT_AREA_H_
|
||||
#ifndef _INCLUDE__BASE__INTERNAL__STACK_AREA_H_
|
||||
#define _INCLUDE__BASE__INTERNAL__STACK_AREA_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/thread.h>
|
||||
@ -24,12 +24,12 @@
|
||||
#include <sys/mman.h>
|
||||
|
||||
|
||||
static inline void flush_context_area()
|
||||
static inline void flush_stack_area()
|
||||
{
|
||||
using namespace Genode;
|
||||
|
||||
void * const base = (void *) Native_config::context_area_virtual_base();
|
||||
size_t const size = Native_config::context_area_virtual_size();
|
||||
void * const base = (void *) Native_config::stack_area_virtual_base();
|
||||
size_t const size = Native_config::stack_area_virtual_size();
|
||||
|
||||
int ret;
|
||||
if ((ret = lx_munmap(base, size)) < 0) {
|
||||
@ -39,14 +39,14 @@ static inline void flush_context_area()
|
||||
}
|
||||
|
||||
|
||||
static inline Genode::addr_t reserve_context_area()
|
||||
static inline Genode::addr_t reserve_stack_area()
|
||||
{
|
||||
using namespace Genode;
|
||||
|
||||
int const flags = MAP_ANONYMOUS | MAP_PRIVATE;
|
||||
int const prot = PROT_NONE;
|
||||
size_t const size = Native_config::context_area_virtual_size();
|
||||
void * const addr_in = (void *)Native_config::context_area_virtual_base();
|
||||
size_t const size = Native_config::stack_area_virtual_size();
|
||||
void * const addr_in = (void *)Native_config::stack_area_virtual_base();
|
||||
void * const addr_out = lx_mmap(addr_in, size, prot, flags, -1, 0);
|
||||
|
||||
/* reserve at local address failed - unmap incorrect mapping */
|
||||
@ -61,4 +61,4 @@ static inline Genode::addr_t reserve_context_area()
|
||||
return (addr_t) addr_out;
|
||||
}
|
||||
|
||||
#endif /* _INCLUDE__BASE__INTERNAL__CONTEXT_AREA_H_ */
|
||||
#endif /* _INCLUDE__BASE__INTERNAL__STACK_AREA_H_ */
|
@ -13,16 +13,16 @@
|
||||
|
||||
PHDRS
|
||||
{
|
||||
context_area PT_LOAD FLAGS(0);
|
||||
stack_area PT_LOAD FLAGS(0);
|
||||
}
|
||||
|
||||
SECTIONS
|
||||
{
|
||||
. = 0x40000000;
|
||||
_context_area_start = .;
|
||||
_stack_area_start = .;
|
||||
/*
|
||||
* Since Linux loads ldso page aligned, we align the context area after
|
||||
* Since Linux loads ldso page aligned, we align the stack area after
|
||||
* loading to a 1 MiB boundary, therefore we reserve one MiB more here.
|
||||
*/
|
||||
.context_area : { . += 0x10100000; } : context_area
|
||||
.stack_area : { . += 0x10100000; } : stack_area
|
||||
}
|
@ -14,6 +14,6 @@
|
||||
SECTIONS
|
||||
{
|
||||
. = 0x40000000;
|
||||
_context_area_start = .;
|
||||
.context_area : { . += 0x10000000; }
|
||||
_stack_area_start = .;
|
||||
.stack_area : { . += 0x10000000; }
|
||||
}
|
@ -20,9 +20,9 @@
|
||||
extern "C" int raw_write_str(const char *str);
|
||||
|
||||
/**
|
||||
* Define context area
|
||||
* Define stack area
|
||||
*/
|
||||
Genode::addr_t _context_area_start;
|
||||
Genode::addr_t _stack_area_start;
|
||||
|
||||
|
||||
enum { verbose_atexit = false };
|
||||
@ -137,7 +137,7 @@ namespace Genode {
|
||||
struct Thread_meta_data
|
||||
{
|
||||
/**
|
||||
* Filled out by 'thread_start' function in the context of the new
|
||||
* Filled out by 'thread_start' function in the stack of the new
|
||||
* thread
|
||||
*/
|
||||
Thread_base * const thread_base;
|
||||
@ -419,7 +419,7 @@ Thread_base::Thread_base(size_t weight, const char *name, size_t stack_size,
|
||||
PERR("pthread_create failed (returned %d, errno=%d)",
|
||||
ret, errno);
|
||||
destroy(env()->heap(), _tid.meta_data);
|
||||
throw Context_alloc_failed();
|
||||
throw Out_of_stack_space();
|
||||
}
|
||||
|
||||
_tid.meta_data->wait_for_construction();
|
||||
|
Reference in New Issue
Block a user