4 // Fraunhofer Institut fuer offene Kommunikationssysteme (FOKUS)
5 // Kompetenzzentrum fuer Satelitenkommunikation (SatCom)
6 // Stefan Bund <stefan.bund@fokus.fraunhofer.de>
8 // This program is free software; you can redistribute it and/or modify
9 // it under the terms of the GNU General Public License as published by
10 // the Free Software Foundation; either version 2 of the License, or
11 // (at your option) any later version.
13 // This program is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 // GNU General Public License for more details.
18 // You should have received a copy of the GNU General Public License
19 // along with this program; if not, write to the
20 // Free Software Foundation, Inc.,
21 // 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
23 #ifndef HH_LLAddressing_
24 #define HH_LLAddressing_ 1
27 #include <boost/range/iterator_range.hpp>
28 #include <boost/utility/enable_if.hpp>
29 #include <boost/type_traits.hpp>
31 #include <sys/socket.h>
32 #include <netpacket/packet.h>
34 #include "SocketPolicy.hh"
35 #include "FileHandle.hh"
36 #include "GenericAddressingPolicy.hh"
38 //#include "LLAddressing.mpp"
39 #include "LLAddressing.ih"
40 ///////////////////////////////hh.p////////////////////////////////////////
48 // Right now we use an arbitrary ForwardRange (see Boost.Range)
49 // as the representation for a hardware address. The restrictions
51 // a) the range must never be larger than 8 elements
52 // b) the value_type must be convertible to unsigend char
53 // and really we need only a single-pass range.
55 // Since a hardware address is so short (a maximum of 8
56 // bytes), in the aftermath I think a simple container holding
57 // a maximum of 8 unsigned chars (e.g. Boost.Array with
58 // additional length parameter) will be much simpler and
59 // probably even more efficient. This should have a conversion
60 // constructor from an arbitrary ForwardRange to make it
61 // compatible e.g. with the Packet library.
63 // However, since I have implemented it already as it is now,
64 // I'll leave it as it is ...
66 typedef boost::iterator_range<unsigned char const *> LLAddress;
69 // And this is for bind
70 explicit LLSocketAddress(unsigned protocol, std::string interface="");
71 explicit LLSocketAddress(std::string interface);
72 // This is for sending packets ..
73 // We must use enable_if here, so this constructor will not hide
74 // above constructor if passed a plain int or short argument
75 template <class ForwardRange>
76 explicit LLSocketAddress(ForwardRange const & address, std::string interface="",
77 typename boost::enable_if_c<! boost::is_integral<ForwardRange>::value >::type * = 0);
81 unsigned protocol() const;
82 std::string interface() const;
83 unsigned arptype() const;
84 unsigned pkttype() const;
85 LLAddress address() const;
87 // The mutating interface is purposely restricted to allow only
88 // changing those members, which are sensible to be changed.
90 template <class ForwardRange>
91 void address(ForwardRange const & address);
92 void interface(std::string interface);
93 void protocol(unsigned protocol);
95 struct sockaddr * sockaddr_p();
96 struct sockaddr const * sockaddr_p() const;
97 unsigned sockaddr_len() const;
100 struct ::sockaddr_ll addr_;
103 detail::LLAddressFromStringRange llAddress(std::string address);
104 // The enable_if condition here allows only for classes as range.
105 // However, excluding zero-terminated strings (which we want to
106 // pass to above) I cannot think of a non-class ForwardRange
107 // except for academic cases
108 template <class ForwardRange>
109 std::string llAddress(ForwardRange const & address,
110 typename boost::enable_if< boost::is_class<ForwardRange> >::type * = 0);
112 class LLAddressingPolicy
113 : public AddressingPolicyBase,
114 private GenericAddressingPolicy<LLSocketAddress>
117 typedef LLSocketAddress Address;
119 using GenericAddressingPolicy<LLSocketAddress>::local;
120 using GenericAddressingPolicy<LLSocketAddress>::bind;
123 struct InvalidLLSocketAddressException : public std::exception
124 { char const * what() const throw() { return "invalid ll address"; } };
127 ///////////////////////////////hh.e////////////////////////////////////////
128 #include "LLAddressing.cci"
129 #include "LLAddressing.ct"
130 #include "LLAddressing.cti"
131 //#include "LLAddressing.mpp"
137 // c-file-style: "satcom"