Introduce time64 support.
[uclibc-ng.git] / libc / inet / socketcalls.c
blobeb0983698ec9d94778934783d2a36e5435f8a8ee
1 /*
2 * Copyright (C) 2000-2006 Erik Andersen <andersen@uclibc.org>
4 * Licensed under the LGPL v2.1, see the file COPYING.LIB in this tarball.
5 */
7 #include <stddef.h>
8 #include <sys/syscall.h>
9 #include <sys/socket.h>
10 #include <cancel.h>
11 #include <bits/kernel-features.h>
13 #ifdef __NR_socketcall
14 /* Various socketcall numbers */
15 #define SYS_SOCKET 1
16 #define SYS_BIND 2
17 #define SYS_CONNECT 3
18 #define SYS_LISTEN 4
19 #define SYS_ACCEPT 5
20 #define SYS_GETSOCKNAME 6
21 #define SYS_GETPEERNAME 7
22 #define SYS_SOCKETPAIR 8
23 #define SYS_SEND 9
24 #define SYS_RECV 10
25 #define SYS_SENDTO 11
26 #define SYS_RECVFROM 12
27 #define SYS_SHUTDOWN 13
28 #define SYS_SETSOCKOPT 14
29 #define SYS_GETSOCKOPT 15
30 #define SYS_SENDMSG 16
31 #define SYS_RECVMSG 17
32 #define SYS_ACCEPT4 18
33 #define SYS_RECVMMSG 19
34 #define SYS_SENDMMSG 20
35 #endif
37 /* exposed on x86 since Linux commit 9dea5dc921b5f4045a18c63eb92e84dc274d17eb */
38 #if defined(__sparc__) || defined(__i386__)
39 #undef __NR_accept
40 #undef __NR_accept4
41 #undef __NR_bind
42 #undef __NR_connect
43 #undef __NR_getpeername
44 #undef __NR_getsockname
45 #undef __NR_getsockopt
46 #undef __NR_listen
47 #undef __NR_recv
48 #undef __NR_recvfrom
49 #undef __NR_recvmsg
50 #undef __NR_send
51 #undef __NR_sendmsg
52 #undef __NR_sendto
53 #undef __NR_setsockopt
54 #undef __NR_shutdown
55 #undef __NR_socket
56 #undef __NR_socketpair
57 #endif
59 #ifdef L_accept
60 static int __NC(accept)(int sockfd, struct sockaddr *addr, socklen_t *addrlen)
62 # ifdef __NR_accept
63 return INLINE_SYSCALL(accept, 3, sockfd, addr, addrlen);
64 # elif defined(__NR_socketcall)
65 unsigned long args[3];
67 args[0] = sockfd;
68 args[1] = (unsigned long) addr;
69 args[2] = (unsigned long) addrlen;
71 return __socketcall(SYS_ACCEPT, args);
72 # endif
74 CANCELLABLE_SYSCALL(int, accept, (int sockfd, struct sockaddr *addr, socklen_t *addrlen),
75 (sockfd, addr, addrlen))
76 lt_libc_hidden(accept)
77 #endif
79 #ifdef L_accept4
80 static int __NC(accept4)(int fd, struct sockaddr *addr, socklen_t *addrlen, int flags)
82 # ifdef __NR_accept4
83 return INLINE_SYSCALL(accept4, 4, fd, addr, addrlen, flags);
84 # elif defined(__NR_socketcall)
85 unsigned long args[4];
87 args[0] = fd;
88 args[1] = (unsigned long) addr;
89 args[2] = (unsigned long) addrlen;
90 args[3] = flags;
92 return __socketcall(SYS_ACCEPT4, args);
93 #endif
95 CANCELLABLE_SYSCALL(int, accept4, (int fd, struct sockaddr *addr, socklen_t *addrlen, int flags),
96 (fd, addr, addrlen, flags))
97 lt_libc_hidden(accept4)
98 #endif
100 #ifdef L_bind
101 int bind(int sockfd, const struct sockaddr *myaddr, socklen_t addrlen)
103 # ifdef __NR_bind
104 return INLINE_SYSCALL(bind, 3, sockfd, myaddr, addrlen);
105 # elif defined(__NR_socketcall)
106 unsigned long args[3];
108 args[0] = sockfd;
109 args[1] = (unsigned long) myaddr;
110 args[2] = addrlen;
111 return __socketcall(SYS_BIND, args);
112 # endif
114 libc_hidden_def(bind)
115 #endif
117 #ifdef L_connect
118 static int __NC(connect)(int sockfd, const struct sockaddr *saddr, socklen_t addrlen)
120 # ifdef __NR_connect
121 return INLINE_SYSCALL(connect, 3, sockfd, saddr, addrlen);
122 # elif defined(__NR_socketcall)
123 unsigned long args[3];
125 args[0] = sockfd;
126 args[1] = (unsigned long) saddr;
127 args[2] = addrlen;
128 return __socketcall(SYS_CONNECT, args);
129 # endif
131 CANCELLABLE_SYSCALL(int, connect, (int sockfd, const struct sockaddr *saddr, socklen_t addrlen),
132 (sockfd, saddr, addrlen))
133 lt_libc_hidden(connect)
134 #endif
136 #ifdef L_getpeername
137 int getpeername(int sockfd, struct sockaddr *addr, socklen_t *paddrlen)
139 # ifdef __NR_getpeername
140 return INLINE_SYSCALL(getpeername, 3, sockfd, addr, paddrlen);
141 # elif defined(__NR_socketcall)
142 unsigned long args[3];
144 args[0] = sockfd;
145 args[1] = (unsigned long) addr;
146 args[2] = (unsigned long) paddrlen;
147 return __socketcall(SYS_GETPEERNAME, args);
148 # endif
150 #endif
152 #ifdef L_getsockname
153 int getsockname(int sockfd, struct sockaddr *addr, socklen_t * paddrlen)
155 # ifdef __NR_getsockname
156 return INLINE_SYSCALL(getsockname, 3, sockfd, addr, paddrlen);
157 # elif defined(__NR_socketcall)
158 unsigned long args[3];
160 args[0] = sockfd;
161 args[1] = (unsigned long) addr;
162 args[2] = (unsigned long) paddrlen;
163 return __socketcall(SYS_GETSOCKNAME, args);
164 # endif
166 libc_hidden_def(getsockname)
167 #endif
169 #ifdef L_getsockopt
170 int getsockopt(int fd, int level, int optname, void *optval,
171 socklen_t *optlen)
173 # ifdef __NR_getsockopt
174 return INLINE_SYSCALL(getsockopt, 5, fd, level, optname, optval, optlen);
175 # elif defined(__NR_socketcall)
176 unsigned long args[5];
178 args[0] = fd;
179 args[1] = level;
180 args[2] = optname;
181 args[3] = (unsigned long) optval;
182 args[4] = (unsigned long) optlen;
183 return (__socketcall(SYS_GETSOCKOPT, args));
184 # endif
186 #endif
188 #ifdef L_listen
189 int listen(int sockfd, int backlog)
191 # ifdef __NR_listen
192 return INLINE_SYSCALL(listen, 2, sockfd, backlog);
193 # elif defined(__NR_socketcall)
194 unsigned long args[2];
196 args[0] = sockfd;
197 args[1] = backlog;
198 return __socketcall(SYS_LISTEN, args);
199 # endif
201 libc_hidden_def(listen)
202 #endif
204 #ifdef L_recv
205 static ssize_t __NC(recv)(int sockfd, void *buffer, size_t len, int flags)
207 # ifdef __NR_recv
208 return (ssize_t)INLINE_SYSCALL(recv, 4, sockfd, buffer, len, flags);
209 # elif defined __NR_recvfrom && defined _syscall6
210 return __NC(recvfrom)(sockfd, buffer, len, flags, NULL, NULL);
211 # elif defined(__NR_socketcall)
212 unsigned long args[4];
214 args[0] = sockfd;
215 args[1] = (unsigned long) buffer;
216 args[2] = len;
217 args[3] = flags;
218 return (ssize_t)__socketcall(SYS_RECV, args);
219 # endif
221 CANCELLABLE_SYSCALL(ssize_t, recv, (int sockfd, void *buffer, size_t len, int flags),
222 (sockfd, buffer, len, flags))
223 lt_libc_hidden(recv)
224 #endif
226 #ifdef L_recvfrom
227 ssize_t __NC(recvfrom)(int sockfd, void *buffer, size_t len, int flags,
228 struct sockaddr *to, socklen_t *tolen)
230 # if defined __NR_recvfrom && defined _syscall6
231 return (ssize_t)INLINE_SYSCALL(recvfrom, 6, sockfd, buffer, len,
232 flags, to, tolen);
233 # elif defined(__NR_socketcall)
234 unsigned long args[6];
236 args[0] = sockfd;
237 args[1] = (unsigned long) buffer;
238 args[2] = len;
239 args[3] = flags;
240 args[4] = (unsigned long) to;
241 args[5] = (unsigned long) tolen;
242 return (ssize_t)__socketcall(SYS_RECVFROM, args);
243 # endif
245 CANCELLABLE_SYSCALL(ssize_t, recvfrom, (int sockfd, void *buffer, size_t len,
246 int flags, struct sockaddr *to, socklen_t *tolen),
247 (sockfd, buffer, len, flags, to, tolen))
248 lt_libc_hidden(recvfrom)
249 #endif
251 #ifdef L_recvmsg
252 static ssize_t __NC(recvmsg)(int sockfd, struct msghdr *msg, int flags)
254 # ifdef __NR_recvmsg
255 return (ssize_t)INLINE_SYSCALL(recvmsg, 3, sockfd, msg, flags);
256 # elif defined(__NR_socketcall)
257 unsigned long args[3];
259 args[0] = sockfd;
260 args[1] = (unsigned long) msg;
261 args[2] = flags;
262 return (ssize_t)__socketcall(SYS_RECVMSG, args);
263 # endif
265 CANCELLABLE_SYSCALL(ssize_t, recvmsg, (int sockfd, struct msghdr *msg, int flags),
266 (sockfd, msg, flags))
267 lt_libc_hidden(recvmsg)
268 #endif
270 #ifdef L_recvmmsg
271 #ifdef __ASSUME_RECVMMSG_SYSCALL
272 static ssize_t __NC(recvmmsg)(int sockfd, struct mmsghdr *msg, size_t vlen,
273 int flags, struct timespec *tmo)
275 # if defined(__UCLIBC_USE_TIME64__) && defined(__NR_recvmmsg_time64)
276 return (ssize_t)INLINE_SYSCALL(recvmmsg_time64, 5, sockfd, msg, vlen, flags, tmo);
277 # elif defined(__NR_recvmmsg)
278 return (ssize_t)INLINE_SYSCALL(recvmmsg, 5, sockfd, msg, vlen, flags, tmo);
279 # elif __NR_socketcall
280 unsigned long args[5];
282 args[0] = sockfd;
283 args[1] = (unsigned long) msg;
284 args[2] = vlen;
285 args[3] = flags;
286 args[4] = (unsigned long) tmo;
287 return (ssize_t)__socketcall(SYS_RECVMMSG, args);
288 # endif
290 CANCELLABLE_SYSCALL(ssize_t, recvmmsg,
291 (int sockfd, struct mmsghdr *msg, size_t vlen, int flags,
292 struct timespec *tmo),
293 (sockfd, msg, vlen, flags, tmo))
294 lt_libc_hidden(recvmmsg)
295 #endif
296 #endif
298 #ifdef L_send
299 static ssize_t __NC(send)(int sockfd, const void *buffer, size_t len, int flags)
301 # ifdef __NR_send
302 return (ssize_t)INLINE_SYSCALL(send, 4, sockfd, buffer, len, flags);
303 # elif defined __NR_sendto && defined _syscall6
304 return __NC(sendto)(sockfd, buffer, len, flags, NULL, 0);
305 # elif defined(__NR_socketcall)
306 unsigned long args[4];
308 args[0] = sockfd;
309 args[1] = (unsigned long) buffer;
310 args[2] = len;
311 args[3] = flags;
312 return (ssize_t)__socketcall(SYS_SEND, args);
313 # endif
315 CANCELLABLE_SYSCALL(ssize_t, send, (int sockfd, const void *buffer, size_t len, int flags),
316 (sockfd, buffer, len, flags))
317 lt_libc_hidden(send)
318 #endif
320 #ifdef L_sendmsg
321 static ssize_t __NC(sendmsg)(int sockfd, const struct msghdr *msg, int flags)
323 # ifdef __NR_sendmsg
324 return (ssize_t)INLINE_SYSCALL(sendmsg, 3, sockfd, msg, flags);
325 # elif defined(__NR_socketcall)
326 unsigned long args[3];
328 args[0] = sockfd;
329 args[1] = (unsigned long) msg;
330 args[2] = flags;
331 return (ssize_t)__socketcall(SYS_SENDMSG, args);
332 # endif
334 CANCELLABLE_SYSCALL(ssize_t, sendmsg, (int sockfd, const struct msghdr *msg, int flags),
335 (sockfd, msg, flags))
336 lt_libc_hidden(sendmsg)
337 #endif
339 #ifdef L_sendmmsg
340 #ifdef __ASSUME_SENDMMSG_SYSCALL
341 static ssize_t __NC(sendmmsg)(int sockfd, struct mmsghdr *msg, size_t vlen,
342 int flags)
344 # ifdef __NR_sendmmsg
345 return (ssize_t)INLINE_SYSCALL(sendmmsg, 4, sockfd, msg, vlen, flags);
346 # elif __NR_socketcall
347 unsigned long args[4];
349 args[0] = sockfd;
350 args[1] = (unsigned long) msg;
351 args[2] = vlen;
352 args[3] = flags;
353 return (ssize_t)__socketcall(SYS_SENDMMSG, args);
354 # endif
356 CANCELLABLE_SYSCALL(ssize_t, sendmmsg,
357 (int sockfd, struct mmsghdr *msg, size_t vlen, int flags),
358 (sockfd, msg, vlen, flags))
359 lt_libc_hidden(sendmmsg)
360 #endif
361 #endif
363 #ifdef L_sendto
364 ssize_t __NC(sendto)(int sockfd, const void *buffer, size_t len, int flags,
365 const struct sockaddr *to, socklen_t tolen)
367 # if defined __NR_sendto && defined _syscall6
368 return (ssize_t)INLINE_SYSCALL(sendto, 6, sockfd, buffer, len, flags, to, tolen);
369 # elif defined(__NR_socketcall)
370 unsigned long args[6];
372 args[0] = sockfd;
373 args[1] = (unsigned long) buffer;
374 args[2] = len;
375 args[3] = flags;
376 args[4] = (unsigned long) to;
377 args[5] = tolen;
378 return (ssize_t)__socketcall(SYS_SENDTO, args);
379 # endif
381 CANCELLABLE_SYSCALL(ssize_t, sendto, (int sockfd, const void *buffer, size_t len,
382 int flags, const struct sockaddr *to, socklen_t tolen),
383 (sockfd, buffer, len, flags, to, tolen))
384 lt_libc_hidden(sendto)
385 #endif
387 #ifdef L_setsockopt
388 int setsockopt(int fd, int level, int optname, const void *optval, socklen_t optlen)
390 # ifdef __NR_setsockopt
391 return INLINE_SYSCALL(setsockopt, 5, fd, level, optname, optval, optlen);
392 # elif defined(__NR_socketcall)
393 unsigned long args[5];
395 args[0] = fd;
396 args[1] = level;
397 args[2] = optname;
398 args[3] = (unsigned long) optval;
399 args[4] = optlen;
400 return __socketcall(SYS_SETSOCKOPT, args);
401 # endif
403 libc_hidden_def(setsockopt)
404 #endif
406 #ifdef L_shutdown
407 int shutdown(int sockfd, int how)
409 # ifdef __NR_shutdown
410 return INLINE_SYSCALL(shutdown, 2, sockfd, how);
411 # elif defined(__NR_socketcall)
412 unsigned long args[2];
414 args[0] = sockfd;
415 args[1] = how;
416 return __socketcall(SYS_SHUTDOWN, args);
417 # endif
419 #endif
421 #ifdef L_socket
422 int socket(int family, int type, int protocol)
424 # ifdef __NR_socket
425 return INLINE_SYSCALL(socket, 3, family, type, protocol);
426 # elif defined(__NR_socketcall)
427 unsigned long args[3];
429 args[0] = family;
430 args[1] = type;
431 args[2] = (unsigned long) protocol;
432 return __socketcall(SYS_SOCKET, args);
433 # endif
435 libc_hidden_def(socket)
436 #endif
438 #ifdef L_socketpair
439 int socketpair(int family, int type, int protocol, int sockvec[2])
441 # ifdef __NR_socketpair
442 return INLINE_SYSCALL(socketpair, 4, family, type, protocol, sockvec);
443 # elif defined(__NR_socketcall)
444 unsigned long args[4];
446 args[0] = family;
447 args[1] = type;
448 args[2] = protocol;
449 args[3] = (unsigned long) sockvec;
450 return __socketcall(SYS_SOCKETPAIR, args);
451 # endif
453 #endif