Make local capability interface explicit. Fix #139.

Introduce a factory-, and dereference method for local capabilities. These are
capabilities that reference objects of services, which are known to be used
protection-domain internally only. To support the new Capability class methods
a protected constructor and accessor to the local object's pointer is needed
in the platform's capability base-classes. For further discussion details please
refer issue #139.
This commit is contained in:
Stefan Kalkowski 2012-03-06 15:55:44 +01:00 committed by Norman Feske
parent 56586ae7b0
commit fa377f0df5
11 changed files with 94 additions and 17 deletions

View File

@ -112,6 +112,11 @@ namespace Genode {
Native_thread_id _tid; /* global thread ID */
int _local_name; /* global unique object ID */
protected:
Native_capability(void* ptr) : _local_name((int)ptr) {
_tid.tid = Codezero::NILTHREAD; }
public:
/**
@ -131,6 +136,7 @@ namespace Genode {
bool valid() const { return _tid.tid != Codezero::NILTHREAD; }
int local_name() const { return _local_name; }
void* local() const { return (void*)_local_name; }
int dst() const { return _tid.tid; }
Native_thread_id tid() const { return _tid; }

View File

@ -74,6 +74,11 @@ namespace Genode {
Fiasco::l4_threadid_t _tid;
long _local_name;
protected:
Native_capability(void *ptr)
: _tid(Fiasco::invalid_l4_threadid_t()), _local_name((long)ptr) { }
public:
/**
@ -85,6 +90,8 @@ namespace Genode {
long local_name() const { return _local_name; }
Fiasco::l4_threadid_t dst() const { return _tid; }
void* local() const { return (void*)_local_name; }
bool valid() const { return l4_is_invalid_id(_tid) == 0; }

View File

@ -60,6 +60,10 @@ namespace Genode {
Native_thread _cap_sel;
int _unique_id;
protected:
Native_capability(void* ptr) : _unique_id((int)ptr) { }
public:
/**
@ -73,9 +77,10 @@ namespace Genode {
Native_capability(Native_thread cap_sel, int unique_id)
: _cap_sel(cap_sel), _unique_id(unique_id) { }
int local_name() const { return _unique_id; }
Native_thread dst() const { return _cap_sel; }
Native_thread_id tid() const { return _cap_sel; }
int local_name() const { return _unique_id; }
void* local() const { return (void*)_unique_id; }
Native_thread dst() const { return _cap_sel; }
Native_thread_id tid() const { return _cap_sel; }
bool valid() const { return _cap_sel.valid() && _unique_id != 0; }

View File

@ -27,6 +27,10 @@ namespace Genode {
long _local_name;
protected:
Native_capability(void* ptr) : _local_name((long)ptr) { }
public:
Native_capability() : _local_name(0) { }
@ -35,6 +39,7 @@ namespace Genode {
bool valid() const { return _local_name != 0; }
int local_name() const { return _local_name; }
void* local() const { return (void*)_local_name; }
int dst() const { return 0; }
Native_thread_id tid() const { return 0; }
};

View File

@ -108,6 +108,10 @@ namespace Genode {
long _tid; /* target thread */
long _local_name;
protected:
Native_capability(void* ptr) : _local_name((long)ptr) { }
public:
/**
@ -117,6 +121,8 @@ namespace Genode {
long local_name() const { return _local_name; }
void* local() const { return (void*)_local_name; }
bool valid() const { return _tid != 0; }

View File

@ -36,6 +36,10 @@ namespace Genode {
Native_thread_id _tid;
long _local_name;
protected:
Native_capability(void* ptr) : _local_name((long)ptr) {}
public:
Native_capability() : _tid(0), _local_name(0) { }
@ -47,6 +51,8 @@ namespace Genode {
int local_name() const { return _local_name; }
void* local() const { return (void*)_local_name; }
int dst() const { return (int)_tid; }
Native_thread_id tid() const { return _tid; }

View File

@ -58,6 +58,10 @@ namespace Genode {
int _pt_sel;
int _unique_id;
protected:
Native_capability(void* ptr) : _unique_id((int)ptr) {}
public:
/**
@ -74,12 +78,13 @@ namespace Genode {
Native_capability(int pt_sel, int unique_id)
: _pt_sel(pt_sel), _unique_id(unique_id) { }
bool valid() const { return _pt_sel != 0 && _unique_id != 0; }
int local_name() const { return _unique_id; }
int dst() const { return _pt_sel; }
bool valid() const { return _pt_sel != 0 && _unique_id != 0; }
int local_name() const { return _unique_id; }
void* local() const { return (void*)_unique_id; }
int dst() const { return _pt_sel; }
int unique_id() const { return _unique_id; }
int pt_sel() const { return _pt_sel; }
int unique_id() const { return _unique_id; }
int pt_sel() const { return _pt_sel; }
};
typedef int Native_connection_state;

View File

@ -88,6 +88,10 @@ namespace Genode {
Okl4::L4_ThreadId_t _tid;
long _local_name;
protected:
Native_capability(void* ptr) : _local_name((long)ptr) {}
public:
/**
@ -99,6 +103,8 @@ namespace Genode {
long local_name() const { return _local_name; }
Okl4::L4_ThreadId_t dst() const { return _tid; }
void* local() const { return (void*)_local_name; }
bool valid() const { return !Okl4::L4_IsNilThread(_tid); }

View File

@ -69,6 +69,10 @@ namespace Genode {
Pistachio::L4_ThreadId_t _tid;
long _local_name;
protected:
Native_capability(void* ptr) : _local_name((long)ptr) {}
public:
/**
@ -83,6 +87,8 @@ namespace Genode {
long local_name() const { return _local_name; }
Pistachio::L4_ThreadId_t dst() const { return _tid; }
void* local() const { return (void*)_local_name; }
bool valid() const { return !Pistachio::L4_IsNilThread(_tid); }

View File

@ -126,6 +126,14 @@ namespace Genode {
return cap;
}
/**
* Private constructor, should be used by the local-capability
* factory method only.
*
* \param ptr pointer to the local object this capability represents.
*/
Capability(void *ptr) : Untyped_capability(ptr) {}
public:
typedef RPC_INTERFACE Rpc_interface;
@ -148,6 +156,28 @@ namespace Genode {
*/
Capability() { }
/**
* Factory method to construct a local-capability.
*
* Local-capabilities can be used protection-domain internally
* only. They simply incorporate a pointer to some process-local
* object.
*
* \param ptr pointer to the corresponding local object.
* \return a capability that represents the local object.
*/
static Capability<RPC_INTERFACE> local_cap(RPC_INTERFACE* ptr) {
return Capability<RPC_INTERFACE>((void*)ptr); }
/**
* Dereference a local-capability.
*
* \param c the local-capability.
* \return pointer to the corresponding local object.
*/
static RPC_INTERFACE* deref(Capability<RPC_INTERFACE> c) {
return reinterpret_cast<RPC_INTERFACE*>(c.local()); }
/*
* Suppress warning about uninitialized 'ret' variable in 'call'
* functions on compilers that support the #praga. If this is

View File

@ -51,7 +51,8 @@ class Context_area_rm_session : public Rm_session
size_t size, off_t offset,
bool use_local_addr, Local_addr local_addr)
{
Dataspace_component *ds = context_ds[ds_cap.local_name()];
Dataspace_component *ds =
dynamic_cast<Dataspace_component*>(Dataspace_capability::deref(ds_cap));
if (!ds) {
PERR("dataspace for core context does not exist");
return (addr_t)0;
@ -111,14 +112,8 @@ class Context_area_ram_session : public Ram_session
context_ds[i] = new (platform()->core_mem_alloc())
Dataspace_component(size, 0, (addr_t)phys_base, false, true);
/*
* We do not manage the dataspace via an entrypoint because it will
* only be used by the 'context_area_rm_session'. Therefore, we
* construct a "capability" by hand using the context ID as local
* name.
*/
Native_capability cap;
return reinterpret_cap_cast<Ram_dataspace>(Native_capability(cap.dst(), i));
Dataspace_capability cap = Dataspace_capability::local_cap(context_ds[i]);
return static_cap_cast<Ram_dataspace>(cap);
}
void free(Ram_dataspace_capability ds) { PDBG("not yet implemented"); }