*** empty log message ***
[bpt/guile.git] / libguile / net_db.c
CommitLineData
370312ae 1/* "net_db.c" network database support
e282f286 2 * Copyright (C) 1995, 96, 97, 98, 99, 2000 Free Software Foundation, Inc.
370312ae
GH
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2, or (at your option)
7 * any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this software; see the file COPYING. If not, write to
82892bed
JB
16 * the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
17 * Boston, MA 02111-1307 USA
370312ae
GH
18 *
19 * As a special exception, the Free Software Foundation gives permission
20 * for additional uses of the text contained in its release of GUILE.
21 *
22 * The exception is that, if you link the GUILE library with other files
23 * to produce an executable, this does not by itself cause the
24 * resulting executable to be covered by the GNU General Public License.
25 * Your use of that executable is in no way restricted on account of
26 * linking the GUILE library code into it.
27 *
28 * This exception does not however invalidate any other reasons why
29 * the executable file might be covered by the GNU General Public License.
30 *
31 * This exception applies only to the code released by the
32 * Free Software Foundation under the name GUILE. If you copy
33 * code from other Free Software Foundation releases into a copy of
34 * GUILE, as the General Public License permits, the exception does
35 * not apply to the code that you add in this way. To avoid misleading
36 * anyone as to the status of such modified files, you must delete
37 * this exception notice from them.
38 *
39 * If you write modifications of your own for GUILE, it is your choice
40 * whether to permit this exception to apply to your modifications.
82892bed 41 * If you do not wish that, delete this exception notice. */
370312ae 42
1bbd0b84
GB
43/* Software engineering face-lift by Greg J. Badros, 11-Dec-1999,
44 gjb@cs.washington.edu, http://www.cs.washington.edu/homes/gjb */
45
46
370312ae
GH
47/* Written in 1994 by Aubrey Jaffer.
48 * Thanks to Hallvard.Tretteberg@si.sintef.no for inspiration and discussion.
49 * Rewritten by Gary Houston to be a closer interface to the C socket library.
50 * Split into net_db.c and socket.c.
51 */
52\f
53
54#include <stdio.h>
a0599745
MD
55#include "libguile/_scm.h"
56#include "libguile/feature.h"
57#include "libguile/strings.h"
58#include "libguile/vectors.h"
370312ae 59
a0599745
MD
60#include "libguile/validate.h"
61#include "libguile/net_db.h"
370312ae
GH
62
63#ifdef HAVE_STRING_H
64#include <string.h>
65#endif
66
67#include <sys/types.h>
cae76441 68#include <sys/socket.h>
370312ae
GH
69#include <netdb.h>
70#include <netinet/in.h>
71#include <arpa/inet.h>
72
e6393a4a
JB
73/* Some systems do not declare this. Some systems do declare it, as a
74 macro. */
75#ifndef h_errno
7a98cdb9 76extern int h_errno;
e6393a4a 77#endif
7a98cdb9 78
370312ae
GH
79\f
80
81#ifndef STDC_HEADERS
82int close ();
83#endif /* STDC_HEADERS */
84
85extern int inet_aton ();
86
a1ec6916 87SCM_DEFINE (scm_inet_aton, "inet-aton", 1, 0, 0,
1bbd0b84 88 (SCM address),
b380b885
MD
89 "Converts a string containing an Internet host address in the traditional\n"
90 "dotted decimal notation into an integer.\n\n"
91 "@smalllisp\n"
d9b6c170
MD
92 "(inet-aton \"127.0.0.1\") @result{} 2130706433\n\n"
93 "@end smalllisp")
1bbd0b84 94#define FUNC_NAME s_scm_inet_aton
370312ae
GH
95{
96 struct in_addr soka;
97
3b3b36dd 98 SCM_VALIDATE_ROSTRING (1,address);
370312ae
GH
99 if (SCM_SUBSTRP (address))
100 address = scm_makfromstr (SCM_ROCHARS (address), SCM_ROLENGTH (address), 0);
101 if (inet_aton (SCM_ROCHARS (address), &soka) == 0)
1bbd0b84 102 SCM_MISC_ERROR ("bad address", SCM_EOL);
370312ae
GH
103 return scm_ulong2num (ntohl (soka.s_addr));
104}
1bbd0b84 105#undef FUNC_NAME
370312ae
GH
106
107
a1ec6916 108SCM_DEFINE (scm_inet_ntoa, "inet-ntoa", 1, 0, 0,
1bbd0b84 109 (SCM inetid),
b380b885
MD
110 "Converts an integer Internet host address into a string with the\n"
111 "traditional dotted decimal representation.\n\n"
112 "@smalllisp\n"
d9b6c170
MD
113 "(inet-ntoa 2130706433) @result{} \"127.0.0.1\""
114 "@end smalllisp")
1bbd0b84 115#define FUNC_NAME s_scm_inet_ntoa
370312ae
GH
116{
117 struct in_addr addr;
118 char *s;
119 SCM answer;
1bbd0b84 120 addr.s_addr = htonl (SCM_NUM2ULONG (1,inetid));
370312ae
GH
121 s = inet_ntoa (addr);
122 answer = scm_makfromstr (s, strlen (s), 0);
370312ae
GH
123 return answer;
124}
1bbd0b84 125#undef FUNC_NAME
370312ae 126
0e958795 127#ifdef HAVE_INET_NETOF
a1ec6916 128SCM_DEFINE (scm_inet_netof, "inet-netof", 1, 0, 0,
1bbd0b84 129 (SCM address),
b380b885
MD
130 "Returns the network number part of the given integer Internet address.\n\n"
131 "@smalllisp\n"
132 "(inet-netof 2130706433) @result{} 127\n"
133 "@end smalllisp")
1bbd0b84 134#define FUNC_NAME s_scm_inet_netof
370312ae
GH
135{
136 struct in_addr addr;
1bbd0b84 137 addr.s_addr = htonl (SCM_NUM2ULONG (1,address));
370312ae
GH
138 return scm_ulong2num ((unsigned long) inet_netof (addr));
139}
1bbd0b84 140#undef FUNC_NAME
0e958795 141#endif
370312ae 142
0e958795 143#ifdef HAVE_INET_LNAOF
a1ec6916 144SCM_DEFINE (scm_lnaof, "inet-lnaof", 1, 0, 0,
1bbd0b84 145 (SCM address),
b380b885
MD
146 "Returns the local-address-with-network part of the given Internet\n"
147 "address.\n\n"
148 "@smalllisp\n"
149 "(inet-lnaof 2130706433) @result{} 1\n"
150 "@end smalllisp")
1bbd0b84 151#define FUNC_NAME s_scm_lnaof
370312ae
GH
152{
153 struct in_addr addr;
1bbd0b84 154 addr.s_addr = htonl (SCM_NUM2ULONG (1,address));
370312ae
GH
155 return scm_ulong2num ((unsigned long) inet_lnaof (addr));
156}
1bbd0b84 157#undef FUNC_NAME
0e958795 158#endif
370312ae 159
0e958795 160#ifdef HAVE_INET_MAKEADDR
a1ec6916 161SCM_DEFINE (scm_inet_makeaddr, "inet-makeaddr", 2, 0, 0,
1bbd0b84 162 (SCM net, SCM lna),
b380b885
MD
163 "Makes an Internet host address by combining the network number @var{net}\n"
164 "with the local-address-within-network number @var{lna}.\n\n"
165 "@smalllisp\n"
166 "(inet-makeaddr 127 1) @result{} 2130706433\n"
167 "@end smalllisp")
1bbd0b84 168#define FUNC_NAME s_scm_inet_makeaddr
370312ae
GH
169{
170 struct in_addr addr;
171 unsigned long netnum;
172 unsigned long lnanum;
173
2eca09c5 174#if 0 /* GJB:FIXME:: */
3b3b36dd
GB
175 SCM_VALIDATE_INUM_COPY (1,net,netnum);
176 SCM_VALIDATE_INUM_COPY (2,lna,lnanum);
2cf37714
GB
177#else
178 netnum = SCM_NUM2ULONG (1, net);
179 lnanum = SCM_NUM2ULONG (2, lna);
180#endif
370312ae
GH
181 addr = inet_makeaddr (netnum, lnanum);
182 return scm_ulong2num (ntohl (addr.s_addr));
183}
1bbd0b84 184#undef FUNC_NAME
0e958795 185#endif
370312ae 186
5c11cc9d
GH
187SCM_SYMBOL (scm_host_not_found_key, "host-not-found");
188SCM_SYMBOL (scm_try_again_key, "try-again");
189SCM_SYMBOL (scm_no_recovery_key, "no-recovery");
190SCM_SYMBOL (scm_no_data_key, "no-data");
370312ae 191
5c11cc9d
GH
192static void scm_resolv_error (const char *subr, SCM bad_value)
193{
194 if (h_errno == NETDB_INTERNAL)
195 {
196 /* errno supposedly contains a useful value. */
197 scm_syserror (subr);
198 }
199 else
200 {
201 SCM key;
202 const char *errmsg;
203
204 switch (h_errno)
205 {
206 case HOST_NOT_FOUND:
207 key = scm_host_not_found_key;
208 errmsg = "Unknown host";
209 break;
210 case TRY_AGAIN:
211 key = scm_try_again_key;
212 errmsg = "Host name lookup failure";
213 break;
214 case NO_RECOVERY:
215 key = scm_no_recovery_key;
216 errmsg = "Unknown server error";
217 break;
218 case NO_DATA:
219 key = scm_no_data_key;
220 errmsg = "No address associated with name";
221 break;
222 default:
223 scm_misc_error (subr, "Unknown resolver error", SCM_EOL);
224 errmsg = NULL;
225 }
226
227#ifdef HAVE_HSTRERROR
d9b6c170 228 errmsg = (const char *) hstrerror (h_errno);
5c11cc9d
GH
229#endif
230 scm_error (key, subr, errmsg, scm_cons (bad_value, SCM_EOL), SCM_EOL);
231 }
232}
233
234/* Should take an extra arg for address format (will be needed for IPv6).
235 Should use reentrant facilities if available.
370312ae
GH
236 */
237
a1ec6916 238SCM_DEFINE (scm_gethost, "gethost", 0, 1, 0,
1bbd0b84 239 (SCM name),
b380b885
MD
240 "@deffnx procedure gethostbyname hostname\n"
241 "@deffnx procedure gethostbyaddr address\n"
242 "Look up a host by name or address, returning a host object. The\n"
243 "@code{gethost} procedure will accept either a string name or an integer\n"
244 "address; if given no arguments, it behaves like @code{gethostent} (see\n"
245 "below). If a name or address is supplied but the address can not be\n"
246 "found, an error will be thrown to one of the keys:\n"
247 "@code{host-not-found}, @code{try-again}, @code{no-recovery} or\n"
248 "@code{no-data}, corresponding to the equivalent @code{h_error} values.\n"
249 "Unusual conditions may result in errors thrown to the\n"
250 "@code{system-error} or @code{misc_error} keys.")
1bbd0b84 251#define FUNC_NAME s_scm_gethost
370312ae 252{
a8741caa 253 SCM ans = scm_make_vector (SCM_MAKINUM (5), SCM_UNSPECIFIED);
370312ae
GH
254 SCM *ve = SCM_VELTS (ans);
255 SCM lst = SCM_EOL;
256 struct hostent *entry;
257 struct in_addr inad;
258 char **argv;
259 int i = 0;
370312ae
GH
260 if (SCM_UNBNDP (name))
261 {
cd34a384 262#ifdef HAVE_GETHOSTENT
370312ae 263 entry = gethostent ();
cd34a384
JB
264#else
265 entry = NULL;
266#endif
07513939
JB
267 if (! entry)
268 {
269 /* As far as I can tell, there's no good way to tell whether
270 zero means an error or end-of-file. The trick of
271 clearing errno before calling gethostent and checking it
272 afterwards doesn't cut it, because, on Linux, it seems to
273 try to contact some other server (YP?) and fails, which
274 is a benign failure. */
07513939
JB
275 return SCM_BOOL_F;
276 }
370312ae 277 }
0c95b57d 278 else if (SCM_ROSTRINGP (name))
370312ae 279 {
89958ad0 280 SCM_COERCE_SUBSTR (name);
ae2fa5bc 281 entry = gethostbyname (SCM_ROCHARS (name));
370312ae
GH
282 }
283 else
284 {
426b4cde 285 inad.s_addr = htonl (SCM_NUM2ULONG (1,name));
370312ae
GH
286 entry = gethostbyaddr ((char *) &inad, sizeof (inad), AF_INET);
287 }
370312ae 288 if (!entry)
1bbd0b84 289 scm_resolv_error (FUNC_NAME, name);
5c11cc9d
GH
290
291 ve[0] = scm_makfromstr (entry->h_name,
292 (scm_sizet) strlen (entry->h_name), 0);
370312ae
GH
293 ve[1] = scm_makfromstrs (-1, entry->h_aliases);
294 ve[2] = SCM_MAKINUM (entry->h_addrtype + 0L);
295 ve[3] = SCM_MAKINUM (entry->h_length + 0L);
296 if (sizeof (struct in_addr) != entry->h_length)
297 {
298 ve[4] = SCM_BOOL_F;
299 return ans;
300 }
301 for (argv = entry->h_addr_list; argv[i]; i++);
302 while (i--)
303 {
304 inad = *(struct in_addr *) argv[i];
305 lst = scm_cons (scm_ulong2num (ntohl (inad.s_addr)), lst);
306 }
307 ve[4] = lst;
308 return ans;
309}
1bbd0b84 310#undef FUNC_NAME
370312ae
GH
311
312
07513939
JB
313/* In all subsequent getMUMBLE functions, when we're called with no
314 arguments, we're supposed to traverse the tables entry by entry.
315 However, there doesn't seem to be any documented way to distinguish
316 between end-of-table and an error; in both cases the functions
317 return zero. Gotta love Unix. For the time being, we clear errno,
318 and if we get a zero and errno is set, we signal an error. This
319 doesn't seem quite right (what if errno gets set as part of healthy
320 operation?), but it seems to work okay. We'll see. */
321
0e958795 322#if defined(HAVE_GETNETENT) && defined(HAVE_GETNETBYNAME) && defined(HAVE_GETNETBYADDR)
a1ec6916 323SCM_DEFINE (scm_getnet, "getnet", 0, 1, 0,
1bbd0b84 324 (SCM name),
b380b885
MD
325 "@deffnx procedure getnetbyname net-name\n"
326 "@deffnx procedure getnetbyaddr net-number\n"
327 "Look up a network by name or net number in the network database. The\n"
328 "@var{net-name} argument must be a string, and the @var{net-number}\n"
329 "argument must be an integer. @code{getnet} will accept either type of\n"
330 "argument, behaving like @code{getnetent} (see below) if no arguments are\n"
331 "given.")
1bbd0b84 332#define FUNC_NAME s_scm_getnet
370312ae
GH
333{
334 SCM ans;
335 SCM *ve;
336 struct netent *entry;
337
a8741caa 338 ans = scm_make_vector (SCM_MAKINUM (4), SCM_UNSPECIFIED);
370312ae
GH
339 ve = SCM_VELTS (ans);
340 if (SCM_UNBNDP (name))
341 {
07513939 342 errno = 0;
370312ae 343 entry = getnetent ();
07513939
JB
344 if (! entry)
345 {
07513939 346 if (errno)
1bbd0b84 347 SCM_SYSERROR;
07513939
JB
348 else
349 return SCM_BOOL_F;
350 }
370312ae 351 }
0c95b57d 352 else if (SCM_ROSTRINGP (name))
370312ae 353 {
89958ad0 354 SCM_COERCE_SUBSTR (name);
ae2fa5bc 355 entry = getnetbyname (SCM_ROCHARS (name));
370312ae
GH
356 }
357 else
358 {
359 unsigned long netnum;
4638e087 360 netnum = SCM_NUM2ULONG (1, name);
370312ae
GH
361 entry = getnetbyaddr (netnum, AF_INET);
362 }
370312ae 363 if (!entry)
5d2d2ffc 364 SCM_SYSERROR_MSG ("no such network ~A",
07513939 365 scm_listify (name, SCM_UNDEFINED), errno);
370312ae
GH
366 ve[0] = scm_makfromstr (entry->n_name, (scm_sizet) strlen (entry->n_name), 0);
367 ve[1] = scm_makfromstrs (-1, entry->n_aliases);
368 ve[2] = SCM_MAKINUM (entry->n_addrtype + 0L);
369 ve[3] = scm_ulong2num (entry->n_net + 0L);
370 return ans;
371}
1bbd0b84 372#undef FUNC_NAME
0e958795 373#endif
370312ae 374
0e958795 375#ifdef HAVE_GETPROTOENT
a1ec6916 376SCM_DEFINE (scm_getproto, "getproto", 0, 1, 0,
1bbd0b84 377 (SCM name),
b380b885
MD
378 "@deffnx procedure getprotobyname name\n"
379 "@deffnx procedure getprotobynumber number\n"
380 "Look up a network protocol by name or by number. @code{getprotobyname}\n"
381 "takes a string argument, and @code{getprotobynumber} takes an integer\n"
382 "argument. @code{getproto} will accept either type, behaving like\n"
383 "@code{getprotoent} (see below) if no arguments are supplied.")
1bbd0b84 384#define FUNC_NAME s_scm_getproto
370312ae
GH
385{
386 SCM ans;
387 SCM *ve;
388 struct protoent *entry;
389
a8741caa 390 ans = scm_make_vector (SCM_MAKINUM (3), SCM_UNSPECIFIED);
370312ae
GH
391 ve = SCM_VELTS (ans);
392 if (SCM_UNBNDP (name))
393 {
07513939 394 errno = 0;
370312ae 395 entry = getprotoent ();
07513939
JB
396 if (! entry)
397 {
07513939 398 if (errno)
1bbd0b84 399 SCM_SYSERROR;
07513939
JB
400 else
401 return SCM_BOOL_F;
402 }
370312ae 403 }
0c95b57d 404 else if (SCM_ROSTRINGP (name))
370312ae 405 {
89958ad0 406 SCM_COERCE_SUBSTR (name);
ae2fa5bc 407 entry = getprotobyname (SCM_ROCHARS (name));
370312ae
GH
408 }
409 else
410 {
411 unsigned long protonum;
1bbd0b84 412 protonum = SCM_NUM2ULONG (1,name);
370312ae
GH
413 entry = getprotobynumber (protonum);
414 }
370312ae 415 if (!entry)
70d63753 416 SCM_SYSERROR_MSG ("no such protocol ~A",
07513939 417 scm_listify (name, SCM_UNDEFINED), errno);
370312ae
GH
418 ve[0] = scm_makfromstr (entry->p_name, (scm_sizet) strlen (entry->p_name), 0);
419 ve[1] = scm_makfromstrs (-1, entry->p_aliases);
420 ve[2] = SCM_MAKINUM (entry->p_proto + 0L);
421 return ans;
422}
1bbd0b84 423#undef FUNC_NAME
0e958795 424#endif
370312ae 425
370312ae 426static SCM
1bbd0b84 427scm_return_entry (struct servent *entry)
370312ae
GH
428{
429 SCM ans;
430 SCM *ve;
431
a8741caa 432 ans = scm_make_vector (SCM_MAKINUM (4), SCM_UNSPECIFIED);
370312ae
GH
433 ve = SCM_VELTS (ans);
434 ve[0] = scm_makfromstr (entry->s_name, (scm_sizet) strlen (entry->s_name), 0);
435 ve[1] = scm_makfromstrs (-1, entry->s_aliases);
436 ve[2] = SCM_MAKINUM (ntohs (entry->s_port) + 0L);
437 ve[3] = scm_makfromstr (entry->s_proto, (scm_sizet) strlen (entry->s_proto), 0);
370312ae
GH
438 return ans;
439}
440
0e958795 441#ifdef HAVE_GETSERVENT
a1ec6916 442SCM_DEFINE (scm_getserv, "getserv", 0, 2, 0,
1bbd0b84 443 (SCM name, SCM proto),
b380b885
MD
444 "@deffnx procedure getservbyname name protocol\n"
445 "@deffnx procedure getservbyport port protocol\n"
446 "Look up a network service by name or by service number, and return a\n"
447 "network service object. The @var{protocol} argument specifies the name\n"
448 "of the desired protocol; if the protocol found in the network service\n"
449 "database does not match this name, a system error is signalled.\n\n"
450 "The @code{getserv} procedure will take either a service name or number\n"
451 "as its first argument; if given no arguments, it behaves like\n"
452 "@code{getservent} (see below).")
1bbd0b84 453#define FUNC_NAME s_scm_getserv
370312ae
GH
454{
455 struct servent *entry;
456 if (SCM_UNBNDP (name))
457 {
07513939 458 errno = 0;
370312ae 459 entry = getservent ();
07513939
JB
460 if (!entry)
461 {
462 if (errno)
1bbd0b84 463 SCM_SYSERROR;
07513939
JB
464 else
465 return SCM_BOOL_F;
466 }
370312ae
GH
467 return scm_return_entry (entry);
468 }
3b3b36dd 469 SCM_VALIDATE_ROSTRING (2,proto);
89958ad0 470 SCM_COERCE_SUBSTR (proto);
0c95b57d 471 if (SCM_ROSTRINGP (name))
370312ae 472 {
89958ad0 473 SCM_COERCE_SUBSTR (name);
ae2fa5bc 474 entry = getservbyname (SCM_ROCHARS (name), SCM_ROCHARS (proto));
370312ae
GH
475 }
476 else
477 {
3b3b36dd 478 SCM_VALIDATE_INUM (1,name);
ae2fa5bc 479 entry = getservbyport (htons (SCM_INUM (name)), SCM_ROCHARS (proto));
370312ae
GH
480 }
481 if (!entry)
70d63753 482 SCM_SYSERROR_MSG("no such service ~A",
1bbd0b84 483 scm_listify (name, SCM_UNDEFINED), errno);
370312ae
GH
484 return scm_return_entry (entry);
485}
1bbd0b84 486#undef FUNC_NAME
0e958795 487#endif
370312ae 488
0e958795 489#if defined(HAVE_SETHOSTENT) && defined(HAVE_ENDHOSTENT)
a1ec6916 490SCM_DEFINE (scm_sethost, "sethost", 0, 1, 0,
1bbd0b84 491 (SCM arg),
b380b885
MD
492 "If @var{stayopen} is omitted, this is equivalent to @code{endhostent}.\n"
493 "Otherwise it is equivalent to @code{sethostent stayopen}.")
1bbd0b84 494#define FUNC_NAME s_scm_sethost
370312ae
GH
495{
496 if (SCM_UNBNDP (arg))
497 endhostent ();
498 else
499 sethostent (SCM_NFALSEP (arg));
500 return SCM_UNSPECIFIED;
501}
1bbd0b84 502#undef FUNC_NAME
0e958795 503#endif
370312ae 504
0e958795 505#if defined(HAVE_SETNETENT) && defined(HAVE_ENDNETENT)
a1ec6916 506SCM_DEFINE (scm_setnet, "setnet", 0, 1, 0,
1bbd0b84 507 (SCM arg),
b380b885
MD
508 "If @var{stayopen} is omitted, this is equivalent to @code{endnetent}.\n"
509 "Otherwise it is equivalent to @code{setnetent stayopen}.")
1bbd0b84 510#define FUNC_NAME s_scm_setnet
370312ae
GH
511{
512 if (SCM_UNBNDP (arg))
513 endnetent ();
514 else
515 setnetent (SCM_NFALSEP (arg));
516 return SCM_UNSPECIFIED;
517}
1bbd0b84 518#undef FUNC_NAME
0e958795 519#endif
370312ae 520
0e958795 521#if defined(HAVE_SETPROTOENT) && defined(HAVE_ENDPROTOENT)
a1ec6916 522SCM_DEFINE (scm_setproto, "setproto", 0, 1, 0,
1bbd0b84 523 (SCM arg),
b380b885
MD
524 "If @var{stayopen} is omitted, this is equivalent to @code{endprotoent}.\n"
525 "Otherwise it is equivalent to @code{setprotoent stayopen}.")
1bbd0b84 526#define FUNC_NAME s_scm_setproto
370312ae
GH
527{
528 if (SCM_UNBNDP (arg))
529 endprotoent ();
530 else
531 setprotoent (SCM_NFALSEP (arg));
532 return SCM_UNSPECIFIED;
533}
1bbd0b84 534#undef FUNC_NAME
0e958795 535#endif
370312ae 536
0e958795 537#if defined(HAVE_SETSERVENT) && defined(HAVE_ENDSERVENT)
a1ec6916 538SCM_DEFINE (scm_setserv, "setserv", 0, 1, 0,
1bbd0b84 539 (SCM arg),
b380b885
MD
540 "If @var{stayopen} is omitted, this is equivalent to @code{endservent}.\n"
541 "Otherwise it is equivalent to @code{setservent stayopen}.")
1bbd0b84 542#define FUNC_NAME s_scm_setserv
370312ae
GH
543{
544 if (SCM_UNBNDP (arg))
545 endservent ();
546 else
547 setservent (SCM_NFALSEP (arg));
548 return SCM_UNSPECIFIED;
549}
1bbd0b84 550#undef FUNC_NAME
0e958795 551#endif
370312ae
GH
552
553
554void
555scm_init_net_db ()
556{
557#ifdef INADDR_ANY
558 scm_sysintern ("INADDR_ANY", scm_ulong2num (INADDR_ANY));
559#endif
560#ifdef INADDR_BROADCAST
561 scm_sysintern ("INADDR_BROADCAST", scm_ulong2num (INADDR_BROADCAST));
562#endif
563#ifdef INADDR_NONE
564 scm_sysintern ("INADDR_NONE", scm_ulong2num (INADDR_NONE));
565#endif
566#ifdef INADDR_LOOPBACK
567 scm_sysintern ("INADDR_LOOPBACK", scm_ulong2num (INADDR_LOOPBACK));
568#endif
569
570 scm_add_feature ("net-db");
a0599745 571#include "libguile/net_db.x"
370312ae 572}
89e00824
ML
573
574/*
575 Local Variables:
576 c-file-style: "gnu"
577 End:
578*/