1 /* lib/rpc/bindresvport.c */
3 * Copyright (c) 2010, Oracle America, Inc.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions are met:
10 * * Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in
15 * the documentation and/or other materials provided with the
18 * * Neither the name of the "Oracle America, Inc." nor the names of
19 * its contributors may be used to endorse or promote products
20 * derived from this software without specific prior written permission.
22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
23 * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
24 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
25 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
26 * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
27 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
28 * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
29 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
30 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
31 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
32 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39 #include <sys/types.h>
40 #include <sys/errno.h>
41 #include <sys/socket.h>
42 #include <netinet/in.h>
43 #include <gssrpc/rpc.h>
45 #include "socket-utils.h"
48 * Bind a socket to a privileged IP port
51 bindresvport_sa(int sd, struct sockaddr *sa)
55 struct sockaddr_storage myaddr;
60 #define ENDPORT (IPPORT_RESERVED - 1)
61 #define NPORTS (ENDPORT - STARTPORT + 1)
63 salen = sizeof(myaddr);
65 res = getsockname(sd, sa, &salen);
69 if (!sa_is_inet(sa)) {
74 port = (getpid() % NPORTS) + STARTPORT;
78 for (i = 0; i < NPORTS && res < 0 && errno == EADDRINUSE; i++) {
79 sa_setport(sa, port++);
83 res = bind(sd, sa, sa_socklen(sa));
89 bindresvport(int sd, struct sockaddr_in *sockin)
91 return (bindresvport_sa(sd, (struct sockaddr *)sockin));