xref: /haiku/src/add-ons/kernel/network/stack/interfaces.h (revision 7aa2819c12dc59c791f84ea19839528cf10bb9f2)
1 /*
2  * Copyright 2006-2010, Haiku, Inc. All Rights Reserved.
3  * Distributed under the terms of the MIT License.
4  *
5  * Authors:
6  *		Axel Dörfler, axeld@pinc-software.de
7  */
8 #ifndef INTERFACES_H
9 #define INTERFACES_H
10 
11 
12 #include "routes.h"
13 #include "stack_private.h"
14 
15 #include <net_datalink.h>
16 #include <net_stack.h>
17 
18 #include <Referenceable.h>
19 
20 #include <util/AutoLock.h>
21 #include <util/DoublyLinkedList.h>
22 #include <util/OpenHashTable.h>
23 
24 
25 struct net_device_interface;
26 
27 
28 // Additional address flags
29 #define IFAF_DIRECT_ADDRESS		0x1000
30 
31 
32 struct InterfaceAddress : DoublyLinkedListLinkImpl<InterfaceAddress>,
33 		net_interface_address, Referenceable {
34 								InterfaceAddress();
35 								InterfaceAddress(net_interface* interface,
36 									net_domain* domain);
37 	virtual						~InterfaceAddress();
38 
39 			status_t			SetTo(const ifaliasreq& request);
40 
41 			status_t			SetLocal(const sockaddr* to);
42 			status_t			SetDestination(const sockaddr* to);
43 			status_t			SetMask(const sockaddr* to);
44 
45 			sockaddr**			AddressFor(int32 option);
46 
47 			void				AddDefaultRoutes(int32 option);
48 			void				RemoveDefaultRoutes(int32 option);
49 
50 			InterfaceAddress*&	HashTableLink() { return fLink; }
51 
52 #if ENABLE_DEBUGGER_COMMANDS
53 			void				Dump(size_t index = 0,
54 									bool hideInterface = false);
55 #endif
56 
57 	static	status_t			Set(sockaddr** _address, const sockaddr* to);
58 	static	sockaddr*			Prepare(sockaddr** _address, size_t length);
59 
60 private:
61 			void				_Init(net_interface* interface,
62 									net_domain* domain);
63 
64 private:
65 			InterfaceAddress*	fLink;
66 };
67 
68 typedef DoublyLinkedList<InterfaceAddress> AddressList;
69 
70 struct domain_datalink {
71 	domain_datalink*	hash_link;
72 	net_domain*			domain;
73 
74 	struct net_datalink_protocol* first_protocol;
75 	struct net_datalink_protocol_module_info* first_info;
76 
77 	// support for binding to an interface
78 	net_route_private	direct_route;
79 	InterfaceAddress	direct_address;
80 };
81 
82 struct DatalinkHashDefinition {
83 	typedef const int KeyType;
84 	typedef domain_datalink ValueType;
85 
86 	DatalinkHashDefinition()
87 	{
88 	}
89 
90 	size_t HashKey(const KeyType& key) const
91 	{
92 		return (size_t)key;
93 	}
94 
95 	size_t Hash(domain_datalink* datalink) const
96 	{
97 		return datalink->domain->family;
98 	}
99 
100 	bool Compare(const KeyType& key, domain_datalink* datalink) const
101 	{
102 		return datalink->domain->family == key;
103 	}
104 
105 	domain_datalink*& GetLink(domain_datalink* datalink) const
106 	{
107 		return datalink->hash_link;
108 	}
109 };
110 
111 typedef BOpenHashTable<DatalinkHashDefinition, true, true> DatalinkTable;
112 
113 
114 class Interface : public DoublyLinkedListLinkImpl<Interface>,
115 		public net_interface, public Referenceable {
116 public:
117 								Interface(const char* name,
118 									net_device_interface* deviceInterface);
119 	virtual						~Interface();
120 
121 			InterfaceAddress*	FirstForFamily(int family);
122 			InterfaceAddress*	FirstUnconfiguredForFamily(int family);
123 			InterfaceAddress*	AddressForDestination(net_domain* domain,
124 									const sockaddr* destination);
125 
126 			status_t			AddAddress(InterfaceAddress* address);
127 			void				RemoveAddress(InterfaceAddress* address);
128 			bool				GetNextAddress(InterfaceAddress** _address);
129 			InterfaceAddress*	AddressAt(size_t index);
130 			size_t				CountAddresses();
131 			void				RemoveAddresses();
132 
133 			status_t			Control(net_domain* domain, int32 option,
134 									ifreq& request, ifreq* userRequest,
135 									size_t length);
136 
137 			void				SetDown();
138 			void				WentDown();
139 
140 			recursive_lock&		Lock() { return fLock; }
141 
142 			net_device_interface* DeviceInterface() { return fDeviceInterface; }
143 
144 			status_t			CreateDomainDatalinkIfNeeded(
145 									net_domain* domain);
146 			domain_datalink*	DomainDatalink(uint8 family);
147 			domain_datalink*	DomainDatalink(net_domain* domain)
148 									{ return DomainDatalink(domain->family); }
149 
150 #if ENABLE_DEBUGGER_COMMANDS
151 			void				Dump() const;
152 #endif
153 
154 private:
155 			status_t			_SetUp();
156 			InterfaceAddress*	_FirstForFamily(int family);
157 			status_t			_ChangeAddress(RecursiveLocker& locker,
158 									InterfaceAddress* address, int32 option,
159 									const sockaddr* oldAddress,
160 									const sockaddr* newAddress);
161 
162 private:
163 			recursive_lock		fLock;
164 			net_device_interface* fDeviceInterface;
165 			AddressList			fAddresses;
166 			DatalinkTable		fDatalinkTable;
167 };
168 
169 typedef DoublyLinkedList<Interface> InterfaceList;
170 
171 
172 status_t init_interfaces();
173 status_t uninit_interfaces();
174 
175 // interfaces
176 status_t add_interface(const char* name, net_domain_private* domain,
177 	const ifaliasreq& request, net_device_interface* deviceInterface);
178 void remove_interface(Interface* interface);
179 void interface_removed_device_interface(net_device_interface* deviceInterface);
180 
181 status_t add_interface_address(Interface* interface, net_domain_private* domain,
182 	const ifaliasreq& request);
183 status_t update_interface_address(InterfaceAddress* interfaceAddress,
184 	int32 option, const sockaddr* oldAddress, const sockaddr* newAddress);
185 
186 Interface* get_interface(net_domain* domain, uint32 index);
187 Interface* get_interface(net_domain* domain, const char* name);
188 Interface* get_interface_for_device(net_domain* domain, uint32 index);
189 Interface* get_interface_for_link(net_domain* domain, const sockaddr* address);
190 InterfaceAddress* get_interface_address(const struct sockaddr* address);
191 InterfaceAddress* get_interface_address_for_destination(net_domain* domain,
192 	const sockaddr* destination);
193 InterfaceAddress* get_interface_address_for_link(net_domain* domain,
194 	const sockaddr* linkAddress, bool unconfiguredOnly);
195 
196 uint32 count_interfaces();
197 status_t list_interfaces(int family, void* buffer, size_t* _bufferSize);
198 
199 
200 #endif	// INTERFACES_H
201