xref: /haiku/src/add-ons/kernel/network/stack/stack_interface.cpp (revision 746cac055adc6ac3308c7bc2d29040fb95689cc9)
1 /*
2  * Copyright 2008, Ingo Weinhold, ingo_weinhold@gmx.de.
3  * Distributed under the terms of the MIT License.
4  */
5 
6 #include "stack_private.h"
7 
8 
9 /*	Interface module providing networking to the kernel.
10 */
11 
12 
13 static status_t
14 stack_interface_open(int family, int type, int protocol, net_socket** _socket)
15 {
16 	return gNetSocketModule.open_socket(family, type, protocol, _socket);
17 }
18 
19 
20 static status_t
21 stack_interface_close(net_socket* socket)
22 {
23 	return gNetSocketModule.close(socket);
24 }
25 
26 
27 static status_t
28 stack_interface_free(net_socket* socket)
29 {
30 	return gNetSocketModule.free(socket);
31 }
32 
33 
34 static status_t
35 stack_interface_bind(net_socket* socket, const struct sockaddr* address,
36 	socklen_t addressLength)
37 {
38 	return gNetSocketModule.bind(socket, address, addressLength);
39 }
40 
41 
42 static status_t
43 stack_interface_shutdown(net_socket* socket, int how)
44 {
45 	return gNetSocketModule.shutdown(socket, how);
46 }
47 
48 
49 static status_t
50 stack_interface_connect(net_socket* socket, const struct sockaddr* address,
51 	socklen_t addressLength)
52 {
53 	return gNetSocketModule.connect(socket, address, addressLength);
54 }
55 
56 
57 static status_t
58 stack_interface_listen(net_socket* socket, int backlog)
59 {
60 	return gNetSocketModule.listen(socket, backlog);
61 }
62 
63 
64 static status_t
65 stack_interface_accept(net_socket* socket, struct sockaddr* address,
66 	socklen_t* _addressLength, net_socket** _acceptedSocket)
67 {
68 	return gNetSocketModule.accept(socket, address, _addressLength,
69 		_acceptedSocket);
70 }
71 
72 
73 static ssize_t
74 stack_interface_recv(net_socket* socket, void* data, size_t length, int flags)
75 {
76 	return gNetSocketModule.receive(socket, NULL, data, length, flags);
77 }
78 
79 
80 static ssize_t
81 stack_interface_recvfrom(net_socket* socket, void* data, size_t length,
82 	int flags, struct sockaddr* address, socklen_t* _addressLength)
83 {
84 	msghdr message;
85 	iovec vecs[1] = { { data, length } };
86 	message.msg_name = address;
87 	if (_addressLength != NULL)
88 		message.msg_namelen = *_addressLength;
89 	else
90 		message.msg_namelen = 0;
91 	message.msg_iov = vecs;
92 	message.msg_iovlen = 1;
93 	message.msg_control = NULL;
94 	message.msg_controllen = 0;
95 	message.msg_flags = 0;
96 
97 	status_t error = gNetSocketModule.receive(socket, &message, data, length,
98 		flags);
99 	if (error != B_OK)
100 		return error;
101 
102 	*_addressLength = message.msg_namelen;
103 	return B_OK;
104 }
105 
106 
107 static ssize_t
108 stack_interface_recvmsg(net_socket* socket, struct msghdr* message, int flags)
109 {
110 	void* buffer = NULL;
111 	size_t len = 0;
112 	if (message->msg_iovlen > 0) {
113 		buffer = message->msg_iov[0].iov_base;
114 		len = message->msg_iov[0].iov_len;
115 	}
116 
117 	return gNetSocketModule.receive(socket, message, buffer, len, flags);
118 }
119 
120 
121 static ssize_t
122 stack_interface_send(net_socket* socket, const void* data, size_t length,
123 	int flags)
124 {
125 	return gNetSocketModule.send(socket, NULL, data, length, flags);
126 }
127 
128 
129 static ssize_t
130 stack_interface_sendto(net_socket* socket, const void* data, size_t length,
131 	int flags, const struct sockaddr* address, socklen_t addressLength)
132 {
133 	msghdr message;
134 	iovec vecs[1] = { { (void*)data, length } };
135 	message.msg_name = (void*)address;
136 	message.msg_namelen = addressLength;
137 	message.msg_iov = vecs;
138 	message.msg_iovlen = 1;
139 	message.msg_control = NULL;
140 	message.msg_controllen = 0;
141 	message.msg_flags = 0;
142 
143 	return gNetSocketModule.send(socket, &message, data, length, flags);
144 }
145 
146 
147 static ssize_t
148 stack_interface_sendmsg(net_socket* socket, const struct msghdr* message,
149 	int flags)
150 {
151 	void* buffer = NULL;
152 	size_t len = 0;
153 	if (message->msg_iovlen > 0) {
154 		buffer = message->msg_iov[0].iov_base;
155 		len = message->msg_iov[0].iov_len;
156 	}
157 
158 	return gNetSocketModule.send(socket, (msghdr*)message, buffer, len, flags);
159 }
160 
161 
162 static status_t
163 stack_interface_getsockopt(net_socket* socket, int level, int option,
164 	void* value, socklen_t* _length)
165 {
166 	int length = *_length;
167 	status_t error = gNetSocketModule.getsockopt(socket, level, option, value,
168 		&length);
169 	*_length = length;
170 	return error;
171 }
172 
173 
174 static status_t
175 stack_interface_setsockopt(net_socket* socket, int level, int option,
176 	const void* value, socklen_t length)
177 {
178 	return gNetSocketModule.setsockopt(socket, level, option, value, length);
179 }
180 
181 
182 static status_t
183 stack_interface_getpeername(net_socket* socket, struct sockaddr* address,
184 	socklen_t* _addressLength)
185 {
186 	return gNetSocketModule.getpeername(socket, address, _addressLength);
187 }
188 
189 
190 static status_t
191 stack_interface_getsockname(net_socket* socket, struct sockaddr* address,
192 	socklen_t* _addressLength)
193 {
194 	return gNetSocketModule.getsockname(socket, address, _addressLength);
195 }
196 
197 
198 static int
199 stack_interface_sockatmark(net_socket* socket)
200 {
201 // TODO:...
202 	return B_UNSUPPORTED;
203 }
204 
205 
206 static status_t
207 stack_interface_socketpair(int family, int type, int protocol,
208 	net_socket* _sockets[2])
209 {
210 	return gNetSocketModule.socketpair(family, type, protocol, _sockets);
211 }
212 
213 
214 static status_t
215 stack_interface_ioctl(net_socket* socket, uint32 op, void *buffer,
216 	size_t length)
217 {
218 	return gNetSocketModule.control(socket, op, buffer, length);
219 }
220 
221 
222 static status_t
223 stack_interface_select(net_socket* socket, uint8 event, struct selectsync *sync)
224 {
225 	return gNetSocketModule.request_notification(socket, event, sync);
226 }
227 
228 
229 static status_t
230 stack_interface_deselect(net_socket* socket, uint8 event,
231 	struct selectsync *sync)
232 {
233 	return gNetSocketModule.cancel_notification(socket, event, sync);
234 }
235 
236 
237 status_t
238 stack_interface_get_next_socket_stat(int family, uint32 *cookie,
239 	struct net_stat *stat)
240 {
241 	return gNetSocketModule.get_next_stat(cookie, family, stat);
242 }
243 
244 
245 static status_t
246 stack_interface_std_ops(int32 op, ...)
247 {
248 	switch (op) {
249 		case B_MODULE_INIT:
250 			return init_stack();
251 		case B_MODULE_UNINIT:
252 			return uninit_stack();
253 
254 		default:
255 			return B_ERROR;
256 	}
257 }
258 
259 
260 net_stack_interface_module_info gNetStackInterfaceModule = {
261 	{
262 		NET_STACK_INTERFACE_MODULE_NAME,
263 		0,
264 		stack_interface_std_ops
265 	},
266 
267 	&stack_interface_open,
268 	&stack_interface_close,
269 	&stack_interface_free,
270 
271 	&stack_interface_bind,
272 	&stack_interface_shutdown,
273 	&stack_interface_connect,
274 	&stack_interface_listen,
275 	&stack_interface_accept,
276 
277 	&stack_interface_recv,
278 	&stack_interface_recvfrom,
279 	&stack_interface_recvmsg,
280 
281 	&stack_interface_send,
282 	&stack_interface_sendto,
283 	&stack_interface_sendmsg,
284 
285 	&stack_interface_getsockopt,
286 	&stack_interface_setsockopt,
287 
288 	&stack_interface_getpeername,
289 	&stack_interface_getsockname,
290 
291 	&stack_interface_sockatmark,
292 
293 	&stack_interface_socketpair,
294 
295 	&stack_interface_ioctl,
296 	&stack_interface_select,
297 	&stack_interface_deselect,
298 
299 	&stack_interface_get_next_socket_stat
300 };
301