4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
23 * Copyright 2010 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
34 #include <sys/sockio.h>
35 #include <netinet/in.h>
36 #include <sys/socket.h>
41 self_check(char *hostname
)
44 struct sioc_addrreq areq
;
46 struct hostent
*hostinfo
;
52 struct sockaddr_in6 ipv6addr
;
56 * We cannot specify AI_DEFAULT since it includes AI_ADDRCONFIG.
57 * Localhost name resolution will fail if no IP interfaces other than
58 * loopback are plumbed and AI_ADDRCONFIG is specified, and this
59 * causes localhost mounts to fail.
63 if ((s
= socket(family
, SOCK_DGRAM
, 0)) < 0) {
64 syslog(LOG_ERR
, "self_check: socket: %m");
68 if ((hostinfo
= getipnodebyname(hostname
, family
, flags
,
69 &error_num
)) == NULL
) {
71 if (error_num
== TRY_AGAIN
)
73 "self_check: unknown host: %s (try again later)\n",
77 "self_check: unknown host: %s\n", hostname
);
83 for (hostptr
= hostinfo
->h_addr_list
; *hostptr
; hostptr
++) {
84 bzero(&ipv6addr
, sizeof (ipv6addr
));
85 ipv6addr
.sin6_family
= AF_INET6
;
86 ipv6addr
.sin6_addr
= *((struct in6_addr
*)(*hostptr
));
87 memcpy(&areq
.sa_addr
, (void *)&ipv6addr
, sizeof (ipv6addr
));
89 (void) ioctl(s
, SIOCTMYADDR
, (caddr_t
)&areq
);
90 if (areq
.sa_res
== 1) {
96 freehostent(hostinfo
);
105 * create an ifconf structure that represents all the interfaces
106 * configured for this host. Two buffers are allcated here:
107 * lifc - the ifconf structure returned
108 * lifc->lifc_buf - the list of ifreq structures
109 * Both of the buffers must be freed by the calling routine.
110 * A NULL pointer is returned upon failure. In this case any
111 * data that was allocated before the failure has already been
121 struct lifconf
*lifc
;
123 if ((sock
= socket(AF_INET6
, SOCK_DGRAM
, 0)) < 0) {
124 syslog(LOG_ERR
, "statd:getmyaddrs socket: %m");
125 return ((struct lifconf
*)NULL
);
128 lifn
.lifn_family
= AF_UNSPEC
;
131 if (ioctl(sock
, SIOCGLIFNUM
, (char *)&lifn
) < 0) {
133 "statd:getmyaddrs, get number of interfaces, error: %m");
137 numifs
= lifn
.lifn_count
;
139 lifc
= (struct lifconf
*)malloc(sizeof (struct lifconf
));
142 "statd:getmyaddrs, malloc for lifconf failed: %m");
144 return ((struct lifconf
*)NULL
);
146 buf
= (char *)malloc(numifs
* sizeof (struct lifreq
));
149 "statd:getmyaddrs, malloc for lifreq failed: %m");
152 return ((struct lifconf
*)NULL
);
155 lifc
->lifc_family
= AF_UNSPEC
;
156 lifc
->lifc_flags
= 0;
157 lifc
->lifc_buf
= buf
;
158 lifc
->lifc_len
= numifs
* sizeof (struct lifreq
);
160 if (ioctl(sock
, SIOCGLIFCONF
, (char *)lifc
) < 0) {
161 syslog(LOG_ERR
, "statd:getmyaddrs, SIOCGLIFCONF, error: %m");
165 return ((struct lifconf
*)NULL
);
179 sock
= socket(AF_INET6
, SOCK_DGRAM
, 0);
183 lifn
.lifn_family
= AF_INET6
;
185 if (ioctl(sock
, SIOCGLIFNUM
, (char *)&lifn
) < 0) {
190 if (lifn
.lifn_count
== 0)