fixed word-order issue in password set and password change.
[Samba.git] / source / lib / netmask.c
blob6d710583758689f2391a5437ddf5e3a7b8317ff3
1 /*
2 Unix SMB/Netbios implementation.
3 Version 1.9.
4 code to query kernel netmask
5 Copyright (C) Andrew Tridgell 1998
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 /* working out the netmask for an interface is an incredibly non-portable
24 thing. We have several possible implementations below, and autoconf
25 tries each of them to see what works
27 Note that this file does _not_ include includes.h. That is so this code
28 can be called directly from the autoconf tests. That also means
29 this code cannot use any of the normal Samba debug stuff or defines.
30 This is standalone code.
34 #ifndef AUTOCONF
35 #include "config.h"
36 #endif
38 #ifdef HAVE_NETMASK_IFCONF
40 #include <stdio.h>
41 #include <unistd.h>
42 #include <sys/types.h>
43 #include <sys/socket.h>
44 #include <netinet/in.h>
45 #include <arpa/inet.h>
46 #include <netdb.h>
47 #include <sys/ioctl.h>
48 #include <net/if.h>
50 #ifndef SIOCGIFCONF
51 #include <sys/sockio.h>
52 #endif
55 * Prototype for gcc in fussy mode.
58 int get_netmask(struct in_addr *ipaddr, struct in_addr *nmask);
60 /****************************************************************************
61 get the netmask address for a local interface
62 ****************************************************************************/
63 int get_netmask(struct in_addr *ipaddr, struct in_addr *nmask)
65 struct ifconf ifc;
66 char buff[2048];
67 int fd, i, n;
68 struct ifreq *ifr=NULL;
70 if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) {
71 #ifdef DEBUG
72 fprintf(stderr,"socket failed\n");
73 #endif
74 return -1;
77 ifc.ifc_len = sizeof(buff);
78 ifc.ifc_buf = buff;
79 if (ioctl(fd, SIOCGIFCONF, &ifc) != 0) {
80 #ifdef DEBUG
81 fprintf(stderr,"SIOCGIFCONF failed\n");
82 #endif
83 close(fd);
84 return -1;
87 ifr = ifc.ifc_req;
89 n = ifc.ifc_len / sizeof(struct ifreq);
91 #ifdef DEBUG
92 fprintf(stderr,"%d interfaces - looking for %s\n",
93 n, inet_ntoa(*ipaddr));
94 #endif
96 /* Loop through interfaces, looking for given IP address */
97 for (i=n-1;i>=0;i--) {
98 if (ioctl(fd, SIOCGIFADDR, &ifr[i]) != 0) {
99 #ifdef DEBUG
100 fprintf(stderr,"SIOCGIFADDR failed\n");
101 #endif
102 continue;
105 #ifdef DEBUG
106 fprintf(stderr,"interface %s\n",
107 inet_ntoa((*(struct sockaddr_in *)&ifr[i].ifr_addr).sin_addr));
108 #endif
109 if (ipaddr->s_addr !=
110 (*(struct sockaddr_in *)&ifr[i].ifr_addr).sin_addr.s_addr) {
111 continue;
114 if (ioctl(fd, SIOCGIFNETMASK, &ifr[i]) != 0) {
115 #ifdef DEBUG
116 fprintf(stderr,"SIOCGIFNETMASK failed\n");
117 #endif
118 close(fd);
119 return -1;
121 close(fd);
122 (*nmask) = ((struct sockaddr_in *)&ifr[i].ifr_addr)->sin_addr;
123 #ifdef DEBUG
124 fprintf(stderr,"netmask %s\n", inet_ntoa(*nmask));
125 #endif
126 return 0;
129 #ifdef DEBUG
130 fprintf(stderr,"interface not found\n");
131 #endif
133 close(fd);
134 return -1;
137 #elif defined(HAVE_NETMASK_IFREQ)
139 #include <stdio.h>
140 #include <sys/types.h>
141 #include <sys/socket.h>
142 #include <netinet/in.h>
143 #include <arpa/inet.h>
144 #include <netdb.h>
145 #include <sys/ioctl.h>
146 #include <net/if.h>
148 #ifndef SIOCGIFCONF
149 #include <sys/sockio.h>
150 #endif
152 #ifndef I_STR
153 #include <sys/stropts.h>
154 #endif
157 /****************************************************************************
158 this should cover most of the rest of systems
159 ****************************************************************************/
160 int get_netmask(struct in_addr *ipaddr, struct in_addr *nmask)
162 struct ifreq ifreq;
163 struct strioctl strioctl;
164 struct ifconf *ifc;
165 char buff[2048];
166 int fd, i, n;
167 struct ifreq *ifr=NULL;
169 if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) {
170 #ifdef DEBUG
171 fprintf(stderr,"socket failed\n");
172 #endif
173 return -1;
176 ifc = (struct ifconf *)buff;
177 ifc->ifc_len = BUFSIZ - sizeof(struct ifconf);
178 strioctl.ic_cmd = SIOCGIFCONF;
179 strioctl.ic_dp = (char *)ifc;
180 strioctl.ic_len = sizeof(buff);
181 if (ioctl(fd, I_STR, &strioctl) < 0) {
182 #ifdef DEBUG
183 fprintf(stderr,"SIOCGIFCONF failed\n");
184 #endif
185 close(fd);
186 return -1;
189 ifr = (struct ifreq *)ifc->ifc_req;
191 /* Loop through interfaces, looking for given IP address */
192 n = ifc->ifc_len / sizeof(struct ifreq);
194 for (i = 0; i<n; i++, ifr++) {
195 #ifdef DEBUG
196 fprintf(stderr,"interface %s\n",
197 inet_ntoa((*(struct sockaddr_in *)&ifr->ifr_addr).sin_addr.s_addr));
198 #endif
199 if (ipaddr->s_addr ==
200 (*(struct sockaddr_in *) &ifr->ifr_addr).sin_addr.s_addr) {
201 break;
205 #ifdef DEBUG
206 if (i == n) {
207 fprintf(stderr,"interface not found\n");
208 close(fd);
209 return -1;
211 #endif
213 ifreq = *ifr;
215 strioctl.ic_cmd = SIOCGIFNETMASK;
216 strioctl.ic_dp = (char *)&ifreq;
217 strioctl.ic_len = sizeof(struct ifreq);
218 if (ioctl(fd, I_STR, &strioctl) != 0) {
219 #ifdef DEBUG
220 fprintf(stderr,"Failed SIOCGIFNETMASK\n");
221 #endif
222 close(fd);
223 return -1;
226 close(fd);
227 *nmask = ((struct sockaddr_in *)&ifreq.ifr_addr)->sin_addr;
228 #ifdef DEBUG
229 fprintf(stderr,"netmask %s\n", inet_ntoa(*nmask));
230 #endif
231 return 0;
234 #elif defined(HAVE_NETMASK_AIX)
236 #include <stdio.h>
237 #include <sys/types.h>
238 #include <sys/socket.h>
239 #include <netinet/in.h>
240 #include <arpa/inet.h>
241 #include <netdb.h>
242 #include <sys/ioctl.h>
243 #include <net/if.h>
245 #ifndef SIOCGIFCONF
246 #include <sys/sockio.h>
247 #endif
249 /****************************************************************************
250 this one is for AIX
251 ****************************************************************************/
252 int get_netmask(struct in_addr *ipaddr, struct in_addr *nmask)
254 char buff[2048];
255 int fd, i, n;
256 struct ifconf ifc;
257 struct ifreq *ifr=NULL;
259 if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) {
260 #ifdef DEBUG
261 fprintf(stderr,"socket failed\n");
262 #endif
263 return -1;
267 ifc.ifc_len = sizeof(buff);
268 ifc.ifc_buf = buff;
270 if (ioctl(fd, SIOCGIFCONF, &ifc) != 0) {
271 #ifdef DEBUG
272 fprintf(stderr,"SIOCGIFCONF failed\n");
273 #endif
274 close(fd);
275 return -1;
278 ifr = ifc.ifc_req;
279 /* Loop through interfaces, looking for given IP address */
280 i = ifc.ifc_len;
281 while (i > 0) {
282 #ifdef DEBUG
283 fprintf(stderr,"interface %s\n",
284 inet_ntoa((*(struct sockaddr_in *)&ifr->ifr_addr).sin_addr));
285 #endif
286 if (ipaddr->s_addr ==
287 (*(struct sockaddr_in *) &ifr->ifr_addr).sin_addr.s_addr) {
288 break;
290 i -= ifr->ifr_addr.sa_len + IFNAMSIZ;
291 ifr = (struct ifreq*) ((char*) ifr + ifr->ifr_addr.sa_len +
292 IFNAMSIZ);
296 #ifdef DEBUG
297 if (i <= 0) {
298 fprintf(stderr,"interface not found\n");
299 close(fd);
300 return -1;
302 #endif
304 if (ioctl(fd, SIOCGIFNETMASK, ifr) != 0) {
305 #ifdef DEBUG
306 fprintf(stderr,"SIOCGIFNETMASK failed\n");
307 #endif
308 close(fd);
309 return -1;
312 close(fd);
314 (*nmask) = ((struct sockaddr_in *)&ifr->ifr_addr)->sin_addr;
315 #ifdef DEBUG
316 fprintf(stderr,"netmask %s\n", inet_ntoa(*nmask));
317 #endif
318 return 0;
321 #else /* a dummy version */
322 struct in_addr; /* it may not have been declared before */
323 int get_netmask(struct in_addr *ipaddr, struct in_addr *nmask)
325 return -1;
327 #endif
330 #ifdef AUTOCONF
331 /* this is the autoconf driver to test get_netmask() */
333 main()
335 char buf[1024];
336 struct hostent *hp;
337 struct in_addr ip, nmask;
339 if (gethostname(buf, sizeof(buf)-1) != 0) {
340 fprintf(stderr,"gethostname failed\n");
341 exit(1);
344 hp = gethostbyname(buf);
346 if (!hp) {
347 fprintf(stderr,"gethostbyname failed\n");
348 exit(1);
351 memcpy((char *)&ip, (char *)hp->h_addr, hp->h_length);
353 if (get_netmask(&ip, &nmask) == 0) exit(0);
355 fprintf(stderr,"get_netmask failed\n");
356 exit(1);
358 #endif