// -*- Mode: C++ -*- // vim:ft=cpp /** * \file * Environment interface */ /* * (c) 2008-2009 Adam Lackorzynski , * Alexander Warg , * Björn Döbel * economic rights: Technische Universität Dresden (Germany) * * This file is part of TUD:OS and distributed under the terms of the * GNU General Public License 2. * Please see the COPYING-GPL-2 file for details. * * As a special exception, you may use this file as part of a free software * library without restriction. Specifically, if other files instantiate * templates or use macros or inline functions from this file, or you compile * this file and link it with other files to produce an executable, this * file does not by itself cause the resulting executable to be covered by * the GNU General Public License. This exception does not however * invalidate any other reasons why the executable file might be covered by * the GNU General Public License. */ #pragma once #include #include #include #include #include #include #include namespace L4 { class Scheduler; } /** * L4 Runtime Environment. */ namespace L4Re { /** * C++ interface of the initial environment that is provided to an L4 task. * * The initial environment is provided to each L4 task that is started * by an L4Re conform loader, such as the Moe root task. The initial * environment provides access to a set of initial capabilities and * some additional information about the available resources, such as * free UTCBs (see \link l4_utcb_api Virtual Registers \endlink) and * available entries in capability table (provided by the micro kernel). * * Each of the initial capabilities is stored at a fixed index in the * task's capability table and the L4 runtime environment provides * convenience functions to retrieve the capabilities. See the table below * for an comprehensive overview. * * Name | Object Type | Convenience Function * ------------ | --------------- | -------------------- * parent | L4Re::Parent | L4Re::Env::parent() * user_factory | L4::Factory | L4Re::Env::user_factory() * log | L4Re::Log | L4Re::Env::log() * main_thread | L4::Thread | L4Re::Env::main_thread() * rm | L4Re::Rm | L4Re::Env::rm() * factory | L4::Factory | L4Re::Env::factory() * task | L4::Task | L4Re::Env::task() * scheduler | L4::Scheduler | L4Re::Env::scheduler() * * Additional information found in the initial environment is: * - First free entry in capability table * - The \link l4_utcb_api UTCB \endlink area (as flex page) * - First free UTCB (address in the UTCB area) * * \includefile{l4/re/env} * * For an explanation of the default task capabilites see \ref * l4_default_caps_t. * * For the C interface refer to \ref api_l4re_env. */ class L4_EXPORT Env { private: l4re_env_t _env; public: /** * C++ type for an entry in the initial objects array. */ typedef l4re_env_cap_entry_t Cap_entry; /** * Returns the initial environment for the current task. * * \return Pointer to the initial environment class. * * A typical use of this function is L4Re::Env::env()->\() */ static Env const *env() noexcept { return reinterpret_cast(l4re_global_env); } /** * Object-capability to the parent. * \return Parent object-capability */ L4::Cap parent() const noexcept { return L4::Cap(_env.parent); } /** * Object-capability to the memory allocator. * \return Memory allocator object-capability */ L4::Cap mem_alloc() const noexcept { return L4::Cap(_env.mem_alloc); } /** * Object-capability to the user-level object factory. */ L4::Cap user_factory() const noexcept { return L4::Cap(_env.mem_alloc); } /** * Object-capability to the region map. * \return Region map object-capability */ L4::Cap rm() const noexcept { return L4::Cap(_env.rm); } /** * Object-capability to the logging service. * \return Log object-capability */ L4::Cap log() const noexcept { return L4::Cap(_env.log); } /** * Object-capability of the first user thread. * \return Object-capability of the first user thread. */ L4::Cap main_thread() const noexcept { return L4::Cap(_env.main_thread); } /** * Object-capability of the user task. * \return Object-capability of the user task. */ L4::Cap task() const noexcept { return L4::Cap(L4RE_THIS_TASK_CAP); } /** * Object-capability to the factory object available to the task. * \return Factory object-capability */ L4::Cap factory() const noexcept { return L4::Cap(_env.factory); } /** * First available capability selector. * \return First capability selector. * * First capability selector available for use for in the application. */ l4_cap_idx_t first_free_cap() const noexcept { return _env.first_free_cap; } /** * UTCB area of the task. * \return UTCB area */ l4_fpage_t utcb_area() const noexcept { return _env.utcb_area; } /** * First free UTCB. * \return object-capability * * First free UTCB within the UTCB area available for the application to * use. */ l4_addr_t first_free_utcb() const noexcept { return _env.first_free_utcb; } /** * Get a pointer to the first entry in the initial objects array. * \return A pointer to the first entry in the initial objects array. */ Cap_entry const *initial_caps() const noexcept { return _env.caps; } /** * Get the Cap_entry for the object named \a name. * \param name is the name of the object. * \param l is the length of the name, thus \a name might not be * zero terminated. * \return A pointer to the Cap_entry for the object named \a name, * or NULL if no such object was found. */ Cap_entry const *get(char const *name, unsigned l) const noexcept { return l4re_env_get_cap_l(name, l, &_env); } /** * Get the capability selector for the object named \a name. * \param name is the name of the object. * \param l is the length of the name, thus \a name might not be * zero terminated. * \return A capability selector for the object named \a name, * or an invalid capability selector if no such object was found. */ template< typename T > L4::Cap get_cap(char const *name, unsigned l) const noexcept { if (Cap_entry const *e = get(name, l)) return L4::Cap(e->cap); return L4::Cap(-L4_ENOENT); } /** * Get the capability selector for the object named \a name. * \param name is the name of the object (zero terminated). * \return A capability selector for the object named \a name, * or an invalid capability selector if no such object was found. */ template< typename T > L4::Cap get_cap(char const *name) const noexcept { return get_cap(name, __builtin_strlen(name)); } /** * Set parent object-capability. * \param c Parent object-capability */ void parent(L4::Cap const &c) noexcept { _env.parent = c.cap(); } /** * Set memory allocator object-capability. * \param c Memory allocator object-capability */ void mem_alloc(L4::Cap const &c) noexcept { _env.mem_alloc = c.cap(); } /** * Set region map object-capability. * \param c Region map object-capability */ void rm(L4::Cap const &c) noexcept { _env.rm = c.cap(); } /** * Set log object-capability. * \param c Log object-capability */ void log(L4::Cap const &c) noexcept { _env.log = c.cap(); } /** * Set object-capability of first user thread. * \param c First thread's object-capability */ void main_thread(L4::Cap const &c) noexcept { _env.main_thread = c.cap(); } /** * Set factory object-capability. * \param c Factory object-capability */ void factory(L4::Cap const &c) noexcept { _env.factory = c.cap(); } /** * Set first available capability selector. * \param c First capability selector available to the application. */ void first_free_cap(l4_cap_idx_t c) noexcept { _env.first_free_cap = c; } /** * Set UTCB area of the task. * \param utcbs UTCB area */ void utcb_area(l4_fpage_t utcbs) noexcept { _env.utcb_area = utcbs; } /** * Set first free UTCB. * \param u First UTCB available for the application to use. */ void first_free_utcb(l4_addr_t u) noexcept { _env.first_free_utcb = u; } /** * Get the scheduler capability for the task. * \return The capability selector for the default scheduler used for this * task. */ L4::Cap scheduler() const noexcept { return L4::Cap(_env.scheduler); } /** * Set the scheduler capability. * \param c is the capability to be set as scheduler. */ void scheduler(L4::Cap const &c) noexcept { _env.scheduler = c.cap(); } /** * Set the pointer to the first Cap_entry in the initial objects array. * \param first is the first element in the array. */ void initial_caps(Cap_entry *first) noexcept { _env.caps = first; } }; };