mirror of
https://github.com/genodelabs/genode.git
synced 2025-02-21 18:06:50 +00:00
os: Skeleton for server implementations
This commit is contained in:
parent
94bcd3f1bf
commit
7e35388336
82
os/include/os/server.h
Normal file
82
os/include/os/server.h
Normal file
@ -0,0 +1,82 @@
|
|||||||
|
/*
|
||||||
|
* \brief Skeleton for implementing servers
|
||||||
|
* \author Norman Feske
|
||||||
|
* \date 2013-09-07
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2013 Genode Labs GmbH
|
||||||
|
*
|
||||||
|
* This file is part of the Genode OS framework, which is distributed
|
||||||
|
* under the terms of the GNU General Public License version 2.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE__OS__SERVER_H_
|
||||||
|
#define _INCLUDE__OS__SERVER_H_
|
||||||
|
|
||||||
|
#include <os/signal_rpc_dispatcher.h>
|
||||||
|
|
||||||
|
namespace Server {
|
||||||
|
|
||||||
|
using namespace Genode;
|
||||||
|
|
||||||
|
class Entrypoint
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
|
||||||
|
Rpc_entrypoint &_rpc_ep;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
Entrypoint();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Associate RPC object with the entry point
|
||||||
|
*/
|
||||||
|
template <typename RPC_INTERFACE, typename RPC_SERVER>
|
||||||
|
Capability<RPC_INTERFACE>
|
||||||
|
manage(Rpc_object<RPC_INTERFACE, RPC_SERVER> &obj)
|
||||||
|
{
|
||||||
|
return _rpc_ep.manage(&obj);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Dissolve RPC object from entry point
|
||||||
|
*/
|
||||||
|
template <typename RPC_INTERFACE, typename RPC_SERVER>
|
||||||
|
void dissolve(Rpc_object<RPC_INTERFACE, RPC_SERVER> &obj)
|
||||||
|
{
|
||||||
|
_rpc_ep.dissolve(&obj);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Associate signal dispatcher with entry point
|
||||||
|
*/
|
||||||
|
Signal_context_capability manage(Signal_rpc_dispatcher_base &);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Disassociate signal dispatcher from entry point
|
||||||
|
*/
|
||||||
|
void dissolve(Signal_rpc_dispatcher_base &);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return RPC entrypoint
|
||||||
|
*/
|
||||||
|
Rpc_entrypoint &rpc_ep() { return _rpc_ep; }
|
||||||
|
};
|
||||||
|
|
||||||
|
void wait_and_dispatch_one_signal();
|
||||||
|
|
||||||
|
|
||||||
|
/***********************************************************
|
||||||
|
** Functions to be provided by the server implementation **
|
||||||
|
***********************************************************/
|
||||||
|
|
||||||
|
size_t stack_size();
|
||||||
|
|
||||||
|
char const *name();
|
||||||
|
|
||||||
|
void construct(Entrypoint &);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* _INCLUDE__OS__SERVER_H_ */
|
3
os/lib/mk/server.mk
Normal file
3
os/lib/mk/server.mk
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
SRC_CC = server.cc
|
||||||
|
|
||||||
|
vpath server.cc $(REP_DIR)/src/lib/server
|
125
os/src/lib/server/server.cc
Normal file
125
os/src/lib/server/server.cc
Normal file
@ -0,0 +1,125 @@
|
|||||||
|
/*
|
||||||
|
* \brief Skeleton for implementing servers
|
||||||
|
* \author Norman Feske
|
||||||
|
* \date 2013-09-07
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2013 Genode Labs GmbH
|
||||||
|
*
|
||||||
|
* This file is part of the Genode OS framework, which is distributed
|
||||||
|
* under the terms of the GNU General Public License version 2.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <os/server.h>
|
||||||
|
#include <cap_session/connection.h>
|
||||||
|
|
||||||
|
using namespace Server;
|
||||||
|
|
||||||
|
|
||||||
|
static Cap_session &global_cap_session()
|
||||||
|
{
|
||||||
|
static Cap_connection inst;
|
||||||
|
return inst;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static Rpc_entrypoint &global_rpc_ep()
|
||||||
|
{
|
||||||
|
static Rpc_entrypoint inst(&global_cap_session(),
|
||||||
|
stack_size(),
|
||||||
|
name());
|
||||||
|
return inst;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static Entrypoint &global_ep()
|
||||||
|
{
|
||||||
|
static Server::Entrypoint inst;
|
||||||
|
return inst;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static Genode::Signal_receiver &global_sig_rec()
|
||||||
|
{
|
||||||
|
static Genode::Signal_receiver inst;
|
||||||
|
return inst;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Signal_context_capability Entrypoint::manage(Signal_rpc_dispatcher_base &dispatcher)
|
||||||
|
{
|
||||||
|
return dispatcher.manage(global_sig_rec(), global_rpc_ep());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Server::Entrypoint::dissolve(Signal_rpc_dispatcher_base &dispatcher)
|
||||||
|
{
|
||||||
|
dispatcher.dissolve(global_sig_rec(), global_rpc_ep());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Server::Entrypoint::Entrypoint() : _rpc_ep(global_rpc_ep()) { }
|
||||||
|
|
||||||
|
|
||||||
|
void Server::wait_and_dispatch_one_signal()
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* We call the signal dispatcher outside of the scope of 'Signal'
|
||||||
|
* object because we block the RPC interface in the input handler
|
||||||
|
* when the kill mode gets actived. While kill mode is active, we
|
||||||
|
* do not serve incoming RPC requests but we need to stay responsive
|
||||||
|
* to user input. Hence, we wait for signals in the input dispatcher
|
||||||
|
* in this case. An already existing 'Signal' object would lock the
|
||||||
|
* signal receiver and thereby prevent this nested way of signal
|
||||||
|
* handling.
|
||||||
|
*/
|
||||||
|
Signal_dispatcher_base *dispatcher = 0;
|
||||||
|
unsigned num = 0;
|
||||||
|
|
||||||
|
{
|
||||||
|
Signal sig = global_sig_rec().wait_for_signal();
|
||||||
|
dispatcher = dynamic_cast<Signal_dispatcher_base *>(sig.context());
|
||||||
|
num = sig.num();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (dispatcher)
|
||||||
|
dispatcher->dispatch(num);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
namespace Server {
|
||||||
|
struct Constructor;
|
||||||
|
struct Constructor_component;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
struct Server::Constructor
|
||||||
|
{
|
||||||
|
GENODE_RPC(Rpc_construct, void, construct);
|
||||||
|
GENODE_RPC_INTERFACE(Rpc_construct);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct Server::Constructor_component : Rpc_object<Server::Constructor,
|
||||||
|
Server::Constructor_component>
|
||||||
|
{
|
||||||
|
void construct() { Server::construct(global_ep()); }
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
int main(int argc, char **argv)
|
||||||
|
{
|
||||||
|
static Server::Constructor_component constructor;
|
||||||
|
|
||||||
|
static Server::Entrypoint ep;
|
||||||
|
|
||||||
|
/* call Server::construct in the context of the entrypoint */
|
||||||
|
Capability<Server::Constructor> constructor_cap = ep.manage(constructor);
|
||||||
|
|
||||||
|
constructor_cap.call<Server::Constructor::Rpc_construct>();
|
||||||
|
|
||||||
|
/* process incoming signals */
|
||||||
|
for (;;)
|
||||||
|
Server::wait_and_dispatch_one_signal();
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user