switch to new MPL based Fraunhofer FOKUS Public License
[senf.git] / senf / Socket / SocketProtocol.hh
1 // $Id$
2 //
3 // Copyright (C) 2006
4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
5 //
6 // The contents of this file are subject to the Fraunhofer FOKUS Public License
7 // Version 1.0 (the "License"); you may not use this file except in compliance
8 // with the License. You may obtain a copy of the License at 
9 // http://senf.berlios.de/license.html
10 //
11 // The Fraunhofer FOKUS Public License Version 1.0 is based on, 
12 // but modifies the Mozilla Public License Version 1.1.
13 // See the full license text for the amendments.
14 //
15 // Software distributed under the License is distributed on an "AS IS" basis, 
16 // WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License 
17 // for the specific language governing rights and limitations under the License.
18 //
19 // The Original Code is Fraunhofer FOKUS code.
20 //
21 // The Initial Developer of the Original Code is Fraunhofer-Gesellschaft e.V. 
22 // (registered association), Hansastraße 27 c, 80686 Munich, Germany.
23 // All Rights Reserved.
24 //
25 // Contributor(s):
26 //   Stefan Bund <g0dil@berlios.de>
27
28 /** \file
29     \brief SocketProtocol and ConcreteSocketProtocol public header
30  */
31
32 // The private inheritance idea should indeed work very well: We just need to change the
33 // implementations of body() and protocol() and that of the ProtocolClient/ServerSocketHandle
34 // constructors and the SocketBody constructor. The body and the protocol would still be visible
35 // like several instances because of the private inheritance but we would save the backwards
36 // pointer.
37
38 /** \defgroup protocol_group The Protocol Classes
39
40     \diaimage Protocols.dia
41
42     The socket handle classes and templates only implement the most important socket API methods
43     using the policy framework. To access the complete API, the protocol interface is
44     provided. Access to the protocol interface is only possible via senf::ProtocolClientSocketHandle
45     and senf::ProtocolServerSocketHandle which have the necessary \c protocol() member. This member
46     returns a reference to the protocol class instance which contains members covering all the API
47     functions (mostly setsockopt/getsockopt related calls but there may be more, this is completely
48     up to the implementor of the protocol class) not found in the SocketHandle interface. The
49     protocol interface is specific to the protocol. It's implementation is quite free. The standard
50     protocols are implemented using a simple multiple-inheritance hierarchy as shown above.
51
52     Since the protocol class is protocol specific (how intelligent ...), the protocol class also
53     defines the \e complete socket policy to be used with it's protocol. Complete meaning, that
54     every policy axis must be assigned it's the most specific (that is derived) policy class to be
55     used with the protocol and that no policy axis is allowed to be left unspecified.
56
57     \see
58         \ref handle_group \n
59         \ref policy_group
60  */
61
62 /** \defgroup concrete_protocol_group Protocol Implementations (Concrete Protocol Classes)
63     \ingroup protocol_group
64
65     These protocol classes define concrete and complete protocol implementations. They inherit from
66     ConcreteSocketProtocol and are used with the ProtocolClientSocketHandle and
67     ProtocolServerSocketHandle templates to instantiate socket handles. Appropriate typedefs are
68     always provided.
69
70     Every protocol defines both the protocol and the policy interface provided by that protocol. See
71     the documentation of the protocol classes listed below for more information on the supported
72     protocols. Every protocol class documents it's policy interface. Use the 'list all members' link
73     of the protocol class to find the complete policy interface.
74  */
75
76 /** \defgroup protocol_facets_group Protocol Facets
77     \ingroup protocol_group
78
79     The protocol facets are classes used as building blocks to build concrete protocol classes. Each
80     protocol facet will implement some functional part of the protocol interface. The protocol
81     facets all inherit from SocketProtocol by public \e virtual inheritance. This ensures the
82     accessibility of the socket body from all facets.
83  */
84
85 #ifndef HH_SENF_Socket_SocketProtocol_
86 #define HH_SENF_Socket_SocketProtocol_ 1
87
88 // Custom includes
89 #include <boost/utility.hpp>
90 // Hrmpf ... I have tried very hard, but I just can't find a nice, generic way to clean
91 // up this include
92 #include "SocketHandle.ih"
93
94 //#include "SocketProtocol.mpp"
95 //-/////////////////////////////////////////////////////////////////////////////////////////////////
96
97 namespace senf {
98
99     /// \addtogroup protocol_group
100     //\{
101
102     class SocketPolicyBase;
103
104     /** \brief Socket Protocol base class
105
106         This is the base class of all socket protocol classes. Every protocol class must directly or
107         indirectly inherit from SocketProtocol
108
109         \attention SocketProtocol must \e always be inherited using public \e virtual inheritance.
110      */
111     class SocketProtocol
112         : boost::noncopyable
113     {
114     public:
115         //-////////////////////////////////////////////////////////////////////////
116         // Types
117
118         //-////////////////////////////////////////////////////////////////////////
119         ///\name Structors and default members
120         //\{
121
122         SocketProtocol();
123         virtual ~SocketProtocol() = 0;
124
125         // default default constructor
126         // no copy
127         // no conversion constructors
128
129         //\}
130         //-////////////////////////////////////////////////////////////////////////
131
132         virtual SocketPolicyBase const & policy() const = 0;
133         ///< Access the policy instance
134
135         //-////////////////////////////////////////////////////////////////////////
136         // Virtual interface
137
138         virtual unsigned available() const = 0;
139                                         ///< Return (maximum) number of bytes available for reading
140                                         ///< without < blocking
141                                         /**< This member will check in a (very, sigh) protocol
142                                              dependent way, how many bytes may be read from a socket
143                                              in a single (non-blocking) read operation. If the
144                                              socket does not support reading (viz. NotReadablePolicy
145                                              is set), this member should always return \c 0.
146
147                                              Depending on the protocol, it may not be possible to
148                                              return a good value. In this case, an upper bound may
149                                              be returned (e.g.: When reading from a socket which
150                                              returns ethernet frames, returning 1500 from
151                                              available() is ok). However, this should only be done
152                                              as a last resort. Also beware, that this number should
153                                              not be too large since the socket layer will always
154                                              need to allocate that number of bytes for the data to
155                                              be read. */
156
157         virtual bool eof() const = 0;   ///< Check for end-of-file condition
158                                         /**< This is another check which (like available()) is
159                                              extremely protocol dependent. This member will return
160                                              \c true only, if at end-of-file. If the protocol does
161                                              not support the notion of EOF, this member should
162                                              always return \c false. */
163
164         virtual void close();           ///< Close socket
165                                         /**< This override will automatically \c shutdown() the
166                                              socket whenever it is closed.
167                                              \throws senf::SystemException
168                                              \fixme Move into (at least) BSDSOcketProtocol */
169
170         virtual void terminate() const; ///< Forcibly close socket
171                                         /**< This override will automatically \c shutdown() the
172                                              socket whenever it is called. Additionally it will
173                                              disable SO_LINGER to ensure, that v_terminate will not
174                                              block. Like the overridden method, this member will
175                                              ignore failures and will never throw. It is therefore
176                                              safe to be called from a destructor.
177                                              \fixme Move into (at least) BSDSocketProtocol */
178
179         virtual void state(SocketStateMap & map, unsigned lod) const;
180                                         ///< Return socket state information
181                                         /**< This member is called to add state information to the
182                                              status \a map. The protocol map should provide as
183                                              detailed information as possible. The amount of
184                                              information to be added to the map is selected by the
185                                              \a lod value with a default value of 0. The
186                                              interpretation of the \a lod value is completely
187                                              implementation defined.
188
189                                              Every class derived from SocketProtocol should
190                                              reimplement state(). The reimplemented method should
191                                              call (all) baseclass-implementations of this
192                                              member.
193
194                                              The \a map Argument is a map which associates
195                                              std:string keys with std:string-like values. The map
196                                              keys are interpreted as hierarchical strings with '.'
197                                              as a separator (like hostnames or struct or class
198                                              members). They are automatically sorted correctly.
199
200                                              The values are std:string with one additional feature:
201                                              they allow assignment or conversion from *any* type as
202                                              long as that type is streamable. This simplifies
203                                              assigning non-string values to the map:
204
205                                              \code
206                                                  map["socket.protocol.ip.address"] << peer();
207                                                  map["socket.protocol.tcp.backlog"] << backlog();
208                                              \endcode
209
210                                              This will work even if peer() returns an ip-address
211                                              object or backlog() returns an integer. The values are
212                                              automatically converted to their string representation.
213
214                                              Additionally, if the slot the date is written to is not
215                                              empty, the <tt>\<\<</tt> operator will add add a comma
216                                              as separator. */
217
218     protected:
219         FileHandle fh() const;          ///< Get a FileHandle for this instance
220                                         /**< This member will re turn a FileHandle instance for this
221                                              protocol instance. You may cast this FileHandle
222                                              instance to a ClientSocketHandle / ServerSocketHandle
223                                              as long as you know some of the socket policy using
224                                              static_socket_cast or dynamic_socket_cast */
225
226         int fd() const;                 ///< Get file descriptor
227                                         /**< Returns the file descriptor this protocol instance
228                                              references. This is the same as <tt>fh().fd()</tt> but
229                                              is implemented here since it is needed so often. */
230
231         void fd(int) const;             ///< Initialize file descriptor
232                                         /**< Assigns the file descriptor to the file handle, this
233                                              protocol instance references. Only valid, if the file
234                                              handle has not yet been assigned any descriptor (To
235                                              change the file descriptor association later, use \c
236                                              ::dup2()). */
237
238     private:
239         virtual std::auto_ptr<SocketBody> clone(bool isServer) const = 0;
240         virtual std::auto_ptr<SocketBody> clone(int fd, bool isServer) const = 0;
241         virtual SocketBody & body() const = 0;
242
243         friend class SocketBody;
244     };
245
246     template <class SPolicy> class ClientSocketHandle;
247     template <class SPolicy> class ServerSocketHandle;
248
249     /** \brief Concrete Socket Protocol implementation base class
250
251         ConcreteSocketProtocol is the base class of a concrete socket protocol implementation. The
252         final protocol class must inherit from ConcreteSocketProtocol. The template argument \a
253         SocketPolicy must be set to the complete socket policy of the protocol. \a Self is the name
254         of the final protocol class which inherits this class.
255
256         A protocol implementation may define the protocol interface directly. It can also
257         (additionally) make use of multiple inheritance to combine a set of protocol facets into a
258         specific protocol implementation (i.e. TCPv4SocketProtocol inherits from
259         ConcreteSocketProtocol and from the protocol facets IPv4SocketProtocol, TCPSocketProtocol,
260         BSDSocketProtocol and AddressableBSDSocketProtocol). The protocol facets are not concrete
261         protocols themselves, they are combined to build concrete protocols. This structure will
262         remove a lot of code duplication. It is important to ensure, that the protocol facets do not
263         overlap, since otherwise there will be problems resolving overlapping members.
264
265         \doc init_client init_server
266      */
267     template <class SocketPolicy, class Self>
268     class ConcreteSocketProtocol
269         : public virtual SocketProtocol
270     {
271     public:
272         //-////////////////////////////////////////////////////////////////////////
273         // Types
274
275         typedef SocketPolicy Policy;    ///< The protocols policy
276
277         //-////////////////////////////////////////////////////////////////////////
278         ///\name Structors and default members
279         //\{
280
281         ~ConcreteSocketProtocol() = 0;
282
283         // no default constructor
284         // no copy
285         // no conversion constructors
286
287         //\}
288         //-////////////////////////////////////////////////////////////////////////
289
290         Policy const & policy() const;
291
292     protected:
293         ClientSocketHandle<Policy> clientHandle() const;
294                                         ///< Get client handle for associated socket
295                                         /**< Returns a client handle for the socket associated with
296                                              this protocol instance */
297         ServerSocketHandle<Policy> serverHandle() const;
298                                         ///< Get server handle for associated socket
299                                         /**< Returns a server handle for the socket associated with
300                                              this protocol instance */
301
302     private:
303         virtual std::auto_ptr<SocketBody> clone(bool isServer) const;
304         virtual std::auto_ptr<SocketBody> clone(int fd, bool isServer) const;
305         virtual SocketBody & body() const;
306
307         Policy policy_;
308     };
309
310     //\}
311 }
312
313 //-/////////////////////////////////////////////////////////////////////////////////////////////////
314 #include "SocketProtocol.cci"
315 //#include "SocketProtocol.ct"
316 #include "SocketProtocol.cti"
317 #endif
318
319 \f
320 // Local Variables:
321 // mode: c++
322 // fill-column: 100
323 // c-file-style: "senf"
324 // indent-tabs-mode: nil
325 // ispell-local-dictionary: "american"
326 // compile-command: "scons -u test"
327 // comment-column: 40
328 // End: