L4Re - L4 Runtime Environment
ipc_server
Go to the documentation of this file.
1 // vi:set ft=cpp: -*- Mode: C++ -*-
2 /**
3  * \file
4  * \brief IPC server loop
5  */
6 /*
7  * (c) 2008-2009 Adam Lackorzynski <adam@os.inf.tu-dresden.de>,
8  * Alexander Warg <warg@os.inf.tu-dresden.de>,
9  * Torsten Frenzel <frenzel@os.inf.tu-dresden.de>
10  * economic rights: Technische Universit├Ąt Dresden (Germany)
11  *
12  * This file is part of TUD:OS and distributed under the terms of the
13  * GNU General Public License 2.
14  * Please see the COPYING-GPL-2 file for details.
15  *
16  * As a special exception, you may use this file as part of a free software
17  * library without restriction. Specifically, if other files instantiate
18  * templates or use macros or inline functions from this file, or you compile
19  * this file and link it with other files to produce an executable, this
20  * file does not by itself cause the resulting executable to be covered by
21  * the GNU General Public License. This exception does not however
22  * invalidate any other reasons why the executable file might be covered by
23  * the GNU General Public License.
24  */
25 
26 #pragma once
27 
28 #include <l4/sys/capability>
29 #include <l4/sys/typeinfo_svr>
30 #include <l4/sys/err.h>
31 #include <l4/cxx/ipc_stream>
32 #include <l4/sys/cxx/ipc_epiface>
33 #include <l4/sys/cxx/ipc_server_loop>
34 #include <l4/cxx/type_traits>
35 #include <l4/cxx/exceptions>
36 
37 namespace L4 {
38 
39 /**
40  * \ingroup cxx_ipc_server
41  * \brief Abstract server object to be used with L4::Server and
42  * L4::Basic_registry.
43  * \note Usually L4::Server_object_t is used as a base class when writing
44  * server objects.
45  *
46  * This server object provides an abstract interface that is used by the
47  * L4::Registry_dispatcher model. You can derive subclasses from this
48  * interface and implement application specific server objects.
49  */
50 class Server_object : public Epiface
51 {
52 public:
53  /**
54  * \brief The abstract handler for client requests to the object.
55  * \param rights The rights bits in the invoked capability.
56  * \param ios The Ipc::Iostream for reading the request and writing the reply.
57  * \retval -L4_ENOREPLY Instructs the server loop to not send a reply.
58  * \retval <0 Error, reply with error code.
59  * \retval >=0 Success, reply with return value.
60  *
61  * This function must be implemented by application specific server
62  * objects. The implementation must unmarshall data from the stream (`ios`)
63  * and create a reply by marshalling to the stream (`ios`). For details
64  * about the IPC stream see [IPC stream operators](\ref ipc_stream).
65  *
66  * \note You need to extract the complete message from the \a ios stream
67  * before inserting any reply data or before doing any function call
68  * that may use the UTCB. Otherwise, the incoming message may get lost.
69  */
70  virtual int dispatch(unsigned long rights, Ipc::Iostream &ios) = 0;
71 
72  l4_msgtag_t dispatch(l4_msgtag_t tag, unsigned rights, l4_utcb_t *utcb)
73  {
74  L4::Ipc::Iostream ios(utcb);
75  ios.tag() = tag;
76  int r = dispatch(rights, ios);
77  return ios.prepare_ipc(r);
78  }
79 
80  Cap<Kobject> obj_cap() const
81  { return cap_cast<Kobject>(Epiface::obj_cap()); }
82 };
83 
84 /**
85  * \ingroup cxx_ipc_server
86  * Base class (template) for server implementing server objects.
87  * \tparam IFACE The IPC interface class that defines the interface that shall
88  * be implemented.
89  * \tparam BASE The server object base class (usually L4::Server_object).
90  */
91 template<typename IFACE, typename BASE = L4::Server_object>
92 struct Server_object_t : BASE
93 {
94  /// Data type of the IPC interface definition
95  typedef IFACE Interface;
96 
97  /// \return the server-side buffer demand based in \a IFACE.
98  typename BASE::Demand get_buffer_demand() const
99  { return typename L4::Kobject_typeid<IFACE>::Demand(); }
100 
101  /**
102  * Implementation of the meta protocol based on \a IFACE.
103  * \param ios The IO stream used for receiving the message.
104  *
105  * This function can be used to handle incoming #L4_PROTO_META protcol
106  * requests. The implementation uses the L4::Type_info of \a IFACE
107  * to handle the requests. Call this function in the implementation of
108  * Server_object::dispatch() when the received message tag has protocol
109  * #L4_PROTO_META (L4::Meta::Protocol).
110  */
111  int dispatch_meta_request(L4::Ipc::Iostream &ios)
112  { return L4::Util::handle_meta_request<IFACE>(ios); }
113 
114  /**
115  * Implementation of protocol-based dispatch for this server object.
116  * \param self The this pointer for the object (inherits from
117  * Server_object_t).
118  * \param rights The rights from the received IPC (forwarded to p_dispatch()).
119  * \param ios The message stream for the incoming and the reply message.
120  *
121  * Server objects may call this function from their dispatch() function.
122  * This function reads the protocol ID from the message tag and uses the
123  * p_dispatch code to dispatch to overloaded p_dispatch functions of self.
124  */
125  template<typename THIS>
126  static int proto_dispatch(THIS *self, l4_umword_t rights, L4::Ipc::Iostream &ios)
127  {
128  l4_msgtag_t t;
129  ios >> t;
130  return Kobject_typeid<IFACE>::proto_dispatch(self, t.label(), rights, ios);
131  }
132 };
133 
134 /**
135  * \ingroup cxx_ipc_server
136  * Helper class to implement p_dispatch based server objects.
137  * \tparam Derived The data type of your server object class.
138  * \tparam IFACE The data type providing the interface definition
139  * for the object.
140  * \tparam BASE Optional data-type of the base server object (usually
141  * L4::Server_object)
142  * \implements L4::Server_object
143  *
144  * This class implements the standard dispatch() function of L4::Server_object
145  * and forwards incoming messages to a set of overloaded p_dispatch() functions.
146  * There must be a p_dispatch() function in Derived for each interface provided
147  * by IFACE with the signature
148  * \code int p_dispatch(Iface *, unsigned rights, L4::Ipc::Iostream &) \endcode
149  * that is called for messages with protocol == Iface::Protocol.
150  *
151  * Example signature for L4Re::Dataspace is:
152  * \code int p_dispatch(L4Re::Dataspace *, unsigned, L4::Ipc::Iostream &) \endcode
153  */
154 template<typename Derived, typename IFACE, typename BASE = L4::Server_object>
155 struct Server_object_x : Server_object_t<IFACE, BASE>
156 {
157  /// Implementation forwarding to p_dispatch().
158  int dispatch(l4_umword_t r, L4::Ipc::Iostream &ios)
159  {
160  return Server_object_t<IFACE, BASE>::proto_dispatch(static_cast<Derived *>(this),
161  r, ios);
162  }
163 };
164 
165 /**
166  * \ingroup cxx_ipc_server
167  * Server object base class for handling IRQ messages.
168  *
169  * This server object base class implements the empty interface
170  * (L4::Kobject). The implementation of Server_object::dispatch() must
171  * return -#L4_ENOREPLY, because IRQ messages do not handle replies.
172  */
173 struct Irq_handler_object : Server_object_t<Kobject> {};
174 
175 }