mirror of
https://github.com/genodelabs/genode.git
synced 2025-06-21 16:39:39 +00:00
Remove exceptions from Pd_session interface
This patch replaces exceptions of the PD session RPC interface with result types. The change of the quota-transfer RPC functions required the adaptation of base/quota_transfer.h and base/child.h. The 'alloc_signal_source' method has been renamed to 'signal_source' to avoid an exceedingly long name of the corresponding result type. The Pd_session::map function takes a 'Virt_range' instead of basic-type arguments. The 'Signal_source_capability' alias for 'Capability<Signal_source>' has been removed. Issue #5245
This commit is contained in:
@ -198,24 +198,30 @@ class Core::Pd_session_component : public Session_object<Pd_session>
|
||||
|
||||
bool assign_pci(addr_t, uint16_t) override;
|
||||
|
||||
void map(addr_t, addr_t) override;
|
||||
Map_result map(Pd_session::Virt_range) override;
|
||||
|
||||
|
||||
/****************
|
||||
** Signalling **
|
||||
****************/
|
||||
|
||||
Signal_source_capability alloc_signal_source() override
|
||||
Signal_source_result signal_source() override
|
||||
{
|
||||
_consume_cap(SIG_SOURCE_CAP);
|
||||
try { _consume_cap(SIG_SOURCE_CAP); }
|
||||
catch (Out_of_caps) {
|
||||
return Signal_source_error::OUT_OF_CAPS; }
|
||||
|
||||
Signal_source_result result = Capability<Signal_source>();
|
||||
|
||||
try { return _signal_broker.alloc_signal_source(); }
|
||||
catch (Allocator::Out_of_memory) {
|
||||
_released_cap_silent();
|
||||
throw Out_of_ram();
|
||||
}
|
||||
catch (Out_of_ram) { result = Signal_source_error::OUT_OF_RAM; }
|
||||
catch (Out_of_caps) { result = Signal_source_error::OUT_OF_CAPS; }
|
||||
|
||||
_released_cap_silent();
|
||||
return result;
|
||||
}
|
||||
|
||||
void free_signal_source(Signal_source_capability sig_rec_cap) override
|
||||
void free_signal_source(Capability<Signal_source> sig_rec_cap) override
|
||||
{
|
||||
if (sig_rec_cap.valid()) {
|
||||
_signal_broker.free_signal_source(sig_rec_cap);
|
||||
@ -224,7 +230,7 @@ class Core::Pd_session_component : public Session_object<Pd_session>
|
||||
}
|
||||
|
||||
Alloc_context_result
|
||||
alloc_context(Signal_source_capability sig_rec_cap, Imprint imprint) override
|
||||
alloc_context(Capability<Signal_source> sig_rec_cap, Imprint imprint) override
|
||||
{
|
||||
try {
|
||||
Cap_quota_guard::Reservation cap_costs(_cap_quota_guard(), Cap_quota{1});
|
||||
@ -257,14 +263,19 @@ class Core::Pd_session_component : public Session_object<Pd_session>
|
||||
** RPC capability allocation **
|
||||
*******************************/
|
||||
|
||||
Native_capability alloc_rpc_cap(Native_capability ep) override
|
||||
Alloc_rpc_cap_result alloc_rpc_cap(Native_capability ep) override
|
||||
{
|
||||
/* may throw 'Out_of_caps' */
|
||||
_consume_cap(RPC_CAP);
|
||||
try { _consume_cap(RPC_CAP); }
|
||||
catch (Out_of_caps) {
|
||||
return Alloc_rpc_cap_error::OUT_OF_CAPS; }
|
||||
|
||||
/* may throw 'Out_of_ram' */
|
||||
try { return _rpc_cap_factory.alloc(ep); }
|
||||
catch (...) { _released_cap_silent(); throw; }
|
||||
try {
|
||||
return _rpc_cap_factory.alloc(ep); }
|
||||
catch (...) {
|
||||
_released_cap_silent();
|
||||
return Alloc_rpc_cap_error::OUT_OF_RAM; }
|
||||
}
|
||||
|
||||
void free_rpc_cap(Native_capability cap) override
|
||||
@ -292,10 +303,10 @@ class Core::Pd_session_component : public Session_object<Pd_session>
|
||||
** Capability and RAM trading and accounting **
|
||||
***********************************************/
|
||||
|
||||
void ref_account(Capability<Pd_session>) override;
|
||||
Ref_account_result ref_account(Capability<Pd_session>) override;
|
||||
|
||||
void transfer_quota(Capability<Pd_session>, Cap_quota) override;
|
||||
void transfer_quota(Capability<Pd_session>, Ram_quota) override;
|
||||
Transfer_cap_quota_result transfer_quota(Capability<Pd_session>, Cap_quota) override;
|
||||
Transfer_ram_quota_result transfer_quota(Capability<Pd_session>, Ram_quota) override;
|
||||
|
||||
Cap_quota cap_quota() const override
|
||||
{
|
||||
|
@ -16,7 +16,6 @@
|
||||
|
||||
/* core includes */
|
||||
#include <signal_source_component.h>
|
||||
#include <signal_source/capability.h>
|
||||
#include <signal_context_slab.h>
|
||||
#include <signal_delivery_proxy.h>
|
||||
|
||||
@ -27,12 +26,12 @@ class Core::Signal_broker
|
||||
{
|
||||
private:
|
||||
|
||||
Allocator &_md_alloc;
|
||||
Rpc_entrypoint &_source_ep;
|
||||
Rpc_entrypoint &_context_ep;
|
||||
Signal_source_component _source;
|
||||
Signal_source_capability _source_cap;
|
||||
Signal_context_slab _contexts_slab { _md_alloc };
|
||||
Allocator &_md_alloc;
|
||||
Rpc_entrypoint &_source_ep;
|
||||
Rpc_entrypoint &_context_ep;
|
||||
Signal_source_component _source;
|
||||
Capability<Signal_source> _source_cap;
|
||||
Signal_context_slab _contexts_slab { _md_alloc };
|
||||
Signal_delivery_proxy_component _delivery_proxy { _source_ep };
|
||||
|
||||
public:
|
||||
@ -60,12 +59,12 @@ class Core::Signal_broker
|
||||
free_context(r->cap());
|
||||
}
|
||||
|
||||
Signal_source_capability alloc_signal_source() { return _source_cap; }
|
||||
Capability<Signal_source> alloc_signal_source() { return _source_cap; }
|
||||
|
||||
void free_signal_source(Signal_source_capability) { }
|
||||
void free_signal_source(Capability<Signal_source>) { }
|
||||
|
||||
Signal_context_capability
|
||||
alloc_context(Signal_source_capability, unsigned long imprint)
|
||||
alloc_context(Capability<Signal_source>, unsigned long imprint)
|
||||
{
|
||||
/*
|
||||
* XXX For now, we ignore the signal-source argument as we
|
||||
|
@ -99,78 +99,88 @@ size_t Pd_session_component::dataspace_size(Ram_dataspace_capability ds_cap) con
|
||||
}
|
||||
|
||||
|
||||
void Pd_session_component::ref_account(Capability<Pd_session> pd_cap)
|
||||
Pd_session::Ref_account_result Pd_session_component::ref_account(Capability<Pd_session> pd_cap)
|
||||
{
|
||||
/* the reference account can be defined only once */
|
||||
if (_cap_account.constructed())
|
||||
return;
|
||||
return Ref_account_result::OK;
|
||||
|
||||
if (this->cap() == pd_cap)
|
||||
return;
|
||||
return Ref_account_result::OK;
|
||||
|
||||
Ref_account_result result = Ref_account_result::INVALID_SESSION;
|
||||
|
||||
_ep.apply(pd_cap, [&] (Pd_session_component *pd) {
|
||||
|
||||
if (!pd || !pd->_ram_account.constructed()) {
|
||||
error("invalid PD session specified as ref account");
|
||||
throw Invalid_session();
|
||||
}
|
||||
if (!pd || !pd->_ram_account.constructed())
|
||||
return;
|
||||
|
||||
_cap_account.construct(_cap_quota_guard(), _label, *pd->_cap_account);
|
||||
_ram_account.construct(_ram_quota_guard(), _label, *pd->_ram_account);
|
||||
|
||||
result = Ref_account_result::OK;
|
||||
});
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
void Pd_session_component::transfer_quota(Capability<Pd_session> pd_cap,
|
||||
Cap_quota amount)
|
||||
Pd_session::Transfer_cap_quota_result
|
||||
Pd_session_component::transfer_quota(Capability<Pd_session> pd_cap, Cap_quota amount)
|
||||
{
|
||||
if (!_cap_account.constructed())
|
||||
throw Undefined_ref_account();
|
||||
return Transfer_cap_quota_result::NO_REF_ACCOUNT;
|
||||
|
||||
if (this->cap() == pd_cap)
|
||||
return;
|
||||
return Transfer_cap_quota_result::OK;
|
||||
|
||||
Transfer_cap_quota_result result = Transfer_cap_quota_result::INVALID_SESSION;
|
||||
|
||||
_ep.apply(pd_cap, [&] (Pd_session_component *pd) {
|
||||
|
||||
if (!pd || !pd->_cap_account.constructed())
|
||||
throw Invalid_session();
|
||||
return;
|
||||
|
||||
try {
|
||||
_cap_account->transfer_quota(*pd->_cap_account, amount);
|
||||
diag("transferred ", amount, " caps "
|
||||
"to '", pd->_cap_account->label(), "' (", _cap_account, ")");
|
||||
result = Transfer_cap_quota_result::OK;
|
||||
}
|
||||
catch (Account<Cap_quota>::Unrelated_account) {
|
||||
warning("attempt to transfer cap quota to unrelated PD session");
|
||||
throw Invalid_session(); }
|
||||
catch (Account<Cap_quota>::Unrelated_account) { }
|
||||
catch (Account<Cap_quota>::Limit_exceeded) {
|
||||
throw Out_of_caps(); }
|
||||
result = Transfer_cap_quota_result::OUT_OF_CAPS;
|
||||
}
|
||||
});
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
void Pd_session_component::transfer_quota(Capability<Pd_session> pd_cap,
|
||||
Ram_quota amount)
|
||||
Pd_session::Transfer_ram_quota_result
|
||||
Pd_session_component::transfer_quota(Capability<Pd_session> pd_cap, Ram_quota amount)
|
||||
{
|
||||
if (!_ram_account.constructed())
|
||||
throw Undefined_ref_account();
|
||||
return Transfer_ram_quota_result::NO_REF_ACCOUNT;
|
||||
|
||||
if (this->cap() == pd_cap)
|
||||
return;
|
||||
return Transfer_ram_quota_result::OK;
|
||||
|
||||
Transfer_ram_quota_result result = Transfer_ram_quota_result::INVALID_SESSION;
|
||||
|
||||
_ep.apply(pd_cap, [&] (Pd_session_component *pd) {
|
||||
|
||||
if (!pd || !pd->_ram_account.constructed())
|
||||
throw Invalid_session();
|
||||
return;
|
||||
|
||||
try {
|
||||
_ram_account->transfer_quota(*pd->_ram_account, amount); }
|
||||
catch (Account<Ram_quota>::Unrelated_account) {
|
||||
warning("attempt to transfer RAM quota to unrelated PD session");
|
||||
throw Invalid_session(); }
|
||||
_ram_account->transfer_quota(*pd->_ram_account, amount);
|
||||
result = Transfer_ram_quota_result::OK;
|
||||
}
|
||||
catch (Account<Ram_quota>::Unrelated_account) { }
|
||||
catch (Account<Ram_quota>::Limit_exceeded) {
|
||||
throw Out_of_ram(); }
|
||||
result = Transfer_ram_quota_result::OUT_OF_RAM;
|
||||
}
|
||||
});
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
|
@ -18,9 +18,14 @@
|
||||
|
||||
using namespace Core;
|
||||
|
||||
|
||||
bool Pd_session_component::assign_pci(addr_t, uint16_t) { return true; }
|
||||
|
||||
void Pd_session_component::map(addr_t, addr_t) { }
|
||||
|
||||
Pd_session::Map_result Pd_session_component::map(Pd_session::Virt_range)
|
||||
{
|
||||
return Map_result::OK;
|
||||
}
|
||||
|
||||
|
||||
class System_control_dummy : public System_control
|
||||
|
Reference in New Issue
Block a user