Skip to content

Commit

Permalink
Add recvmmsg and sendmmsg to the generic glibc API.
Browse files Browse the repository at this point in the history
  • Loading branch information
tschwinge committed Nov 20, 2012
1 parent cf9a5d1 commit 123be9d
Show file tree
Hide file tree
Showing 13 changed files with 147 additions and 60 deletions.
25 changes: 25 additions & 0 deletions ChangeLog
Original file line number Diff line number Diff line change
@@ -1,3 +1,28 @@
2012-11-20 Thomas Schwinge <[email protected]>

* sysdeps/unix/sysv/linux/bits/socket.h (struct mmsghdr, recvmmsg)
(sendmmsg): Move declarations...
* socket/sys/socket.h: ... here.
* sysdeps/unix/sysv/linux/recvmmsg.c [!defined __NR_recvmmsg &&
!defined __NR_socketcall] (recvmmsg): Move ENOSYS stub into and
include it from...
* socket/recvmmsg.c: ... this new file.
* sysdeps/unix/sysv/linux/internal_sendmmsg.S [__ASSUME_SENDMMSG]
(sendmmsg): Rename to __sendmmsg, create weak alias and make
definition of __sendmmsg hidden.
* sysdeps/unix/sysv/linux/sendmmsg.c (sendmmsg): Likewise.
[!defined __NR_sendmmsg && !defined __NR_socketcall] (sendmmsg):
Move ENOSYS stub into and include it from...
* socket/sendmmsg.c: ... this new file.
* sysdeps/unix/sysv/linux/Makefile [subdir=socket]
(sysdep_routines): Move recvmmsg and sendmmsg...
* socket/Makefile (routines): ... here.
* socket/Versions (GLIBC_2.17): Add recvmmsg and sendmmsg.
(GLIBC_PRIVATE): Add __sendmmsg.
* include/sys/socket.h (__sendmmsg): Add declarations.
* resolv/res_send.c (send_dg): Invoke __sendmmsg instead of
sendmmsg.

2012-11-20 Joseph Myers <[email protected]>

* sysdeps/ieee754/ldbl-128/s_nearbyintl.c (__nearbyintl): Mark
Expand Down
4 changes: 4 additions & 0 deletions include/sys/socket.h
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,10 @@ extern ssize_t __libc_sendmsg (int __fd, const struct msghdr *__message,
extern ssize_t __sendmsg (int __fd, const struct msghdr *__message,
int __flags) attribute_hidden;

extern int __sendmmsg (int __fd, struct mmsghdr *__vmessages,
unsigned int __vlen, int __flags);
libc_hidden_proto (__sendmmsg)

/* Receive a message as described by MESSAGE from socket FD.
Returns the number of bytes read or -1 for errors. */
extern ssize_t __libc_recvmsg (int __fd, struct msghdr *__message,
Expand Down
2 changes: 1 addition & 1 deletion resolv/res_send.c
Original file line number Diff line number Diff line change
Expand Up @@ -1129,7 +1129,7 @@ send_dg(res_state statp,
reqs[1].msg_hdr.msg_control = NULL;
reqs[1].msg_hdr.msg_controllen = 0;

int ndg = sendmmsg (pfd[0].fd, reqs, 2, MSG_NOSIGNAL);
int ndg = __sendmmsg (pfd[0].fd, reqs, 2, MSG_NOSIGNAL);
if (__builtin_expect (ndg == 2, 1))
{
if (reqs[0].msg_len != buflen
Expand Down
2 changes: 1 addition & 1 deletion socket/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ headers := sys/socket.h sys/un.h bits/sockaddr.h bits/socket.h \
routines := accept bind connect getpeername getsockname getsockopt \
listen recv recvfrom recvmsg send sendmsg sendto \
setsockopt shutdown socket socketpair isfdtype opensock \
sockatmark accept4
sockatmark accept4 recvmmsg sendmmsg

aux := have_sock_cloexec

Expand Down
6 changes: 6 additions & 0 deletions socket/Versions
Original file line number Diff line number Diff line change
Expand Up @@ -34,4 +34,10 @@ libc {
GLIBC_2.10 {
accept4;
}
GLIBC_2.17 {
recvmmsg; sendmmsg;
}
GLIBC_PRIVATE {
__sendmmsg;
}
}
31 changes: 31 additions & 0 deletions socket/recvmmsg.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
/* Receive multiple messages on a socket. Stub version.
Copyright (C) 2010-2012 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with the GNU C Library; if not, see
<http://www.gnu.org/licenses/>. */

#include <errno.h>
#include <sys/socket.h>

/* Receive up to VLEN messages as described by VMESSAGES from socket FD.
Returns the number of bytes read or -1 for errors. */
int
recvmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags,
const struct timespec *tmo)
{
__set_errno (ENOSYS);
return -1;
}
stub_warning (recvmmsg)
32 changes: 32 additions & 0 deletions socket/sendmmsg.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
/* Send multiple messages on a socket. Stub version.
Copyright (C) 2011-2012 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with the GNU C Library; if not, see
<http://www.gnu.org/licenses/>. */

#include <errno.h>
#include <sys/socket.h>

/* Send a VLEN messages as described by VMESSAGES to socket FD.
Returns the number of datagrams successfully written or -1 for errors. */
int
__sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
{
__set_errno (ENOSYS);
return -1;
}
libc_hidden_def (__sendmmsg)
weak_alias (__sendmmsg, sendmmsg)
stub_warning (sendmmsg)
31 changes: 31 additions & 0 deletions socket/sys/socket.h
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,16 @@ typedef union { __SOCKADDR_ALLTYPES
# undef __SOCKADDR_ONETYPE
#endif

#ifdef __USE_GNU
/* For `recvmmsg' and `sendmmsg'. */
struct mmsghdr
{
struct msghdr msg_hdr; /* Actual message header. */
unsigned int msg_len; /* Number of received or sent bytes for the
entry. */
};
#endif


/* Create a new socket of type TYPE in domain DOMAIN, using
protocol PROTOCOL. If PROTOCOL is zero, one is chosen automatically.
Expand Down Expand Up @@ -175,13 +185,34 @@ extern ssize_t recvfrom (int __fd, void *__restrict __buf, size_t __n,
extern ssize_t sendmsg (int __fd, const struct msghdr *__message,
int __flags);

#ifdef __USE_GNU
/* Send a VLEN messages as described by VMESSAGES to socket FD.
Returns the number of datagrams successfully written or -1 for errors.
This function is a cancellation point and therefore not marked with
__THROW. */
extern int sendmmsg (int __fd, struct mmsghdr *__vmessages,
unsigned int __vlen, int __flags);
#endif

/* Receive a message as described by MESSAGE from socket FD.
Returns the number of bytes read or -1 for errors.
This function is a cancellation point and therefore not marked with
__THROW. */
extern ssize_t recvmsg (int __fd, struct msghdr *__message, int __flags);

#ifdef __USE_GNU
/* Receive up to VLEN messages as described by VMESSAGES from socket FD.
Returns the number of bytes read or -1 for errors.
This function is a cancellation point and therefore not marked with
__THROW. */
extern int recvmmsg (int __fd, struct mmsghdr *__vmessages,
unsigned int __vlen, int __flags,
const struct timespec *__tmo);
#endif


/* Put the current value for socket FD's option OPTNAME at protocol level LEVEL
into OPTVAL (which is *OPTLEN bytes long), and set *OPTLEN to the value's
Expand Down
3 changes: 1 addition & 2 deletions sysdeps/unix/sysv/linux/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,7 @@ CFLAGS-malloc.c += -DMORECORE_CLEARS=2
endif

ifeq ($(subdir),socket)
sysdep_routines += internal_accept4 recvmmsg internal_recvmmsg sendmmsg \
internal_sendmmsg
sysdep_routines += internal_accept4 internal_recvmmsg internal_sendmmsg
endif

ifeq ($(subdir),misc)
Expand Down
33 changes: 0 additions & 33 deletions sysdeps/unix/sysv/linux/bits/socket.h
Original file line number Diff line number Diff line change
Expand Up @@ -235,16 +235,6 @@ struct msghdr
int msg_flags; /* Flags on received message. */
};

#ifdef __USE_GNU
/* For `recvmmsg' and 'sendmmsg'. */
struct mmsghdr
{
struct msghdr msg_hdr; /* Actual message header. */
unsigned int msg_len; /* Number of received or sent bytes
for the entry. */
};
#endif

/* Structure used for storage of ancillary data object information. */
struct cmsghdr
{
Expand Down Expand Up @@ -389,27 +379,4 @@ struct linger
int l_linger; /* Time to linger. */
};


__BEGIN_DECLS

#ifdef __USE_GNU
/* Receive up to VLEN messages as described by VMESSAGES from socket FD.
Returns the number of bytes read or -1 for errors.
This function is a cancellation point and therefore not marked with
__THROW. */
extern int recvmmsg (int __fd, struct mmsghdr *__vmessages,
unsigned int __vlen, int __flags,
const struct timespec *__tmo);

/* Send a VLEN messages as described by VMESSAGES to socket FD.
Return the number of datagrams successfully written or -1 for errors.
This function is a cancellation point and therefore not marked with
__THROW. */
extern int sendmmsg (int __fd, struct mmsghdr *__vmessages,
unsigned int __vlen, int __flags);
#endif

__END_DECLS

#endif /* bits/socket.h */
9 changes: 5 additions & 4 deletions sysdeps/unix/sysv/linux/internal_sendmmsg.S
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,14 @@
#include <sys/syscall.h>
#if !defined __NR_sendmmsg && defined __NR_socketcall
# define socket sendmmsg
# ifdef __ASSUME_SENDMMSG
# define __socket sendmmsg
# else
# ifndef __ASSUME_SENDMMSG
# define __socket __internal_sendmmsg
# define NO_WEAK_ALIAS
# endif
# define NARGS 4
# define NEED_CANCELLATION
# define NO_WEAK_ALIAS
# include <socket.S>
# ifdef __ASSUME_SENDMMSG
libc_hidden_def (__sendmmsg)
# endif
#endif
11 changes: 2 additions & 9 deletions sysdeps/unix/sysv/linux/recvmmsg.c
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
/* Copyright (C) 2010 Free Software Foundation, Inc.
/* Copyright (C) 2010-2012 Free Software Foundation, Inc.
This file is part of the GNU C Library.
Contributed by Andreas Schwab <[email protected]>, 2010.
Expand Down Expand Up @@ -88,12 +88,5 @@ recvmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags,
/* When __ASSUME_RECVMMSG recvmmsg is defined in internal_recvmmsg.S. */
# endif
#else
int
recvmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags,
const struct timespec *tmo)
{
__set_errno (ENOSYS);
return -1;
}
stub_warning (recvmmsg)
# include <socket/recvmmsg.c>
#endif
18 changes: 8 additions & 10 deletions sysdeps/unix/sysv/linux/sendmmsg.c
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
/* Copyright (C) 2011 Free Software Foundation, Inc.
/* Copyright (C) 2011-2012 Free Software Foundation, Inc.
This file is part of the GNU C Library.
Contributed by Ulrich Drepper <[email protected]>, 2011.
Expand Down Expand Up @@ -26,7 +26,7 @@

#ifdef __NR_sendmmsg
int
sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
__sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
{
if (SINGLE_THREAD_P)
return INLINE_SYSCALL (sendmmsg, 4, fd, vmessages, vlen, flags);
Expand All @@ -39,6 +39,8 @@ sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)

return result;
}
libc_hidden_def (__sendmmsg)
weak_alias (__sendmmsg, sendmmsg)
#elif defined __NR_socketcall
# ifndef __ASSUME_SENDMMSG
extern int __internal_sendmmsg (int fd, struct mmsghdr *vmessages,
Expand All @@ -48,7 +50,7 @@ extern int __internal_sendmmsg (int fd, struct mmsghdr *vmessages,
static int have_sendmmsg;

int
sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
__sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
{
if (__builtin_expect (have_sendmmsg >= 0, 1))
{
Expand Down Expand Up @@ -81,15 +83,11 @@ sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
__set_errno (ENOSYS);
return -1;
}
libc_hidden_def (__sendmmsg)
weak_alias (__sendmmsg, sendmmsg)
# else
/* When __ASSUME_SENDMMSG sendmmsg is defined in internal_sendmmsg.S. */
# endif
#else
int
sendmmsg (int fd, struct mmsghdr *vmessages, unsigned int vlen, int flags)
{
__set_errno (ENOSYS);
return -1;
}
stub_warning (sendmmsg)
# include <socket/sendmmsg.c>
#endif

0 comments on commit 123be9d

Please sign in to comment.