* socket.c (scm_fill_sockaddr): call htons for sin6_port.
[bpt/guile.git] / libguile / socket.c
1 /* Copyright (C) 1996,1997,1998,2000,2001 Free Software Foundation, Inc.
2 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation; either version 2, or (at your option)
6 * any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this software; see the file COPYING. If not, write to
15 * the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
16 * Boston, MA 02111-1307 USA
17 *
18 * As a special exception, the Free Software Foundation gives permission
19 * for additional uses of the text contained in its release of GUILE.
20 *
21 * The exception is that, if you link the GUILE library with other files
22 * to produce an executable, this does not by itself cause the
23 * resulting executable to be covered by the GNU General Public License.
24 * Your use of that executable is in no way restricted on account of
25 * linking the GUILE library code into it.
26 *
27 * This exception does not however invalidate any other reasons why
28 * the executable file might be covered by the GNU General Public License.
29 *
30 * This exception applies only to the code released by the
31 * Free Software Foundation under the name GUILE. If you copy
32 * code from other Free Software Foundation releases into a copy of
33 * GUILE, as the General Public License permits, the exception does
34 * not apply to the code that you add in this way. To avoid misleading
35 * anyone as to the status of such modified files, you must delete
36 * this exception notice from them.
37 *
38 * If you write modifications of your own for GUILE, it is your choice
39 * whether to permit this exception to apply to your modifications.
40 * If you do not wish that, delete this exception notice. */
41
42 /* Software engineering face-lift by Greg J. Badros, 11-Dec-1999,
43 gjb@cs.washington.edu, http://www.cs.washington.edu/homes/gjb */
44
45 \f
46
47 #include <errno.h>
48
49 #include "libguile/_scm.h"
50 #include "libguile/unif.h"
51 #include "libguile/feature.h"
52 #include "libguile/fports.h"
53 #include "libguile/strings.h"
54 #include "libguile/vectors.h"
55
56 #include "libguile/validate.h"
57 #include "libguile/socket.h"
58
59 #ifdef HAVE_STRING_H
60 #include <string.h>
61 #endif
62 #ifdef HAVE_UNISTD_H
63 #include <unistd.h>
64 #endif
65 #include <sys/types.h>
66 #include <sys/socket.h>
67 #ifdef HAVE_UNIX_DOMAIN_SOCKETS
68 #include <sys/un.h>
69 #endif
70 #include <netinet/in.h>
71 #include <netdb.h>
72 #include <arpa/inet.h>
73
74 #if defined (HAVE_UNIX_DOMAIN_SOCKETS) && !defined (SUN_LEN)
75 #define SUN_LEN(ptr) ((size_t) (((struct sockaddr_un *) 0)->sun_path) \
76 + strlen ((ptr)->sun_path))
77 #endif
78
79 /* we are not currently using socklen_t. it's not defined on all systems,
80 so would need to be checked by configure. in the meantime, plain
81 int is the best alternative. */
82
83 \f
84
85 SCM_DEFINE (scm_htons, "htons", 1, 0, 0,
86 (SCM in),
87 "Return a new integer from @var{value} by converting from host\n"
88 "to network order. @var{value} must be within the range of a C\n"
89 "unsigned short integer.")
90 #define FUNC_NAME s_scm_htons
91 {
92 unsigned short c_in;
93
94 SCM_VALIDATE_INUM_COPY (1,in,c_in);
95 if (c_in != SCM_INUM (in))
96 SCM_OUT_OF_RANGE (1,in);
97
98 return SCM_MAKINUM (htons (c_in));
99 }
100 #undef FUNC_NAME
101
102 SCM_DEFINE (scm_ntohs, "ntohs", 1, 0, 0,
103 (SCM in),
104 "Return a new integer from @var{value} by converting from\n"
105 "network to host order. @var{value} must be within the range of\n"
106 "a C unsigned short integer.")
107 #define FUNC_NAME s_scm_ntohs
108 {
109 unsigned short c_in;
110
111 SCM_VALIDATE_INUM_COPY (1,in,c_in);
112 if (c_in != SCM_INUM (in))
113 SCM_OUT_OF_RANGE (1,in);
114
115 return SCM_MAKINUM (ntohs (c_in));
116 }
117 #undef FUNC_NAME
118
119 SCM_DEFINE (scm_htonl, "htonl", 1, 0, 0,
120 (SCM in),
121 "Return a new integer from @var{value} by converting from host\n"
122 "to network order. @var{value} must be within the range of a C\n"
123 "unsigned long integer.")
124 #define FUNC_NAME s_scm_htonl
125 {
126 unsigned long c_in = SCM_NUM2ULONG (1, in);
127 return scm_ulong2num (htonl (c_in));
128 }
129 #undef FUNC_NAME
130
131 SCM_DEFINE (scm_ntohl, "ntohl", 1, 0, 0,
132 (SCM in),
133 "Return a new integer from @var{value} by converting from\n"
134 "network to host order. @var{value} must be within the range of\n"
135 "a C unsigned long integer.")
136 #define FUNC_NAME s_scm_ntohl
137 {
138 unsigned long c_in = SCM_NUM2ULONG (1, in);
139 return scm_ulong2num (ntohl (c_in));
140 }
141 #undef FUNC_NAME
142
143 SCM_SYMBOL (sym_socket, "socket");
144
145 #define SCM_SOCK_FD_TO_PORT(fd) scm_fdes_to_port (fd, "r+0", sym_socket)
146
147 SCM_DEFINE (scm_socket, "socket", 3, 0, 0,
148 (SCM family, SCM style, SCM proto),
149 "Return a new socket port of the type specified by @var{family},\n"
150 "@var{style} and @var{protocol}. All three parameters are\n"
151 "integers. Supported values for @var{family} are\n"
152 "@code{AF_UNIX}, @code{AF_INET} and @code{AF_INET6}.\n"
153 "Typical values for @var{style} are @code{SOCK_STREAM},\n"
154 "@code{SOCK_DGRAM} and @code{SOCK_RAW}.\n"
155 "\n"
156 "@var{protocol} can be obtained from a protocol name using\n"
157 "@code{getprotobyname}. A value of zero specifies the default\n"
158 "protocol, which is usually right.\n"
159 "\n"
160 "A single socket port cannot by used for communication until it\n"
161 "has been connected to another socket.")
162 #define FUNC_NAME s_scm_socket
163 {
164 int fd;
165
166 SCM_VALIDATE_INUM (1, family);
167 SCM_VALIDATE_INUM (2, style);
168 SCM_VALIDATE_INUM (3, proto);
169 fd = socket (SCM_INUM (family), SCM_INUM (style), SCM_INUM (proto));
170 if (fd == -1)
171 SCM_SYSERROR;
172 return SCM_SOCK_FD_TO_PORT (fd);
173 }
174 #undef FUNC_NAME
175
176 #ifdef HAVE_SOCKETPAIR
177 SCM_DEFINE (scm_socketpair, "socketpair", 3, 0, 0,
178 (SCM family, SCM style, SCM proto),
179 "Return a pair of connected (but unnamed) socket ports of the\n"
180 "type specified by @var{family}, @var{style} and @var{protocol}.\n"
181 "Many systems support only socket pairs of the @code{AF_UNIX}\n"
182 "family. Zero is likely to be the only meaningful value for\n"
183 "@var{protocol}.")
184 #define FUNC_NAME s_scm_socketpair
185 {
186 int fam;
187 int fd[2];
188
189 SCM_VALIDATE_INUM (1,family);
190 SCM_VALIDATE_INUM (2,style);
191 SCM_VALIDATE_INUM (3,proto);
192
193 fam = SCM_INUM (family);
194
195 if (socketpair (fam, SCM_INUM (style), SCM_INUM (proto), fd) == -1)
196 SCM_SYSERROR;
197
198 return scm_cons (SCM_SOCK_FD_TO_PORT (fd[0]), SCM_SOCK_FD_TO_PORT (fd[1]));
199 }
200 #undef FUNC_NAME
201 #endif
202
203 SCM_DEFINE (scm_getsockopt, "getsockopt", 3, 0, 0,
204 (SCM sock, SCM level, SCM optname),
205 "Return the value of a particular socket option for the socket\n"
206 "port @var{socket}. @var{level} is an integer code for type of\n"
207 "option being requested, e.g., @code{SOL_SOCKET} for\n"
208 "socket-level options. @var{optname} is an integer code for the\n"
209 "option required and should be specified using one of the\n"
210 "symbols @code{SO_DEBUG}, @code{SO_REUSEADDR} etc.\n"
211 "\n"
212 "The returned value is typically an integer but @code{SO_LINGER}\n"
213 "returns a pair of integers.")
214 #define FUNC_NAME s_scm_getsockopt
215 {
216 int fd;
217 /* size of optval is the largest supported option. */
218 #ifdef HAVE_STRUCT_LINGER
219 char optval[sizeof (struct linger)];
220 int optlen = sizeof (struct linger);
221 #else
222 char optval[sizeof (scm_sizet)];
223 int optlen = sizeof (scm_sizet);
224 #endif
225 int ilevel;
226 int ioptname;
227
228 sock = SCM_COERCE_OUTPORT (sock);
229 SCM_VALIDATE_OPFPORT (1, sock);
230 SCM_VALIDATE_INUM_COPY (2, level, ilevel);
231 SCM_VALIDATE_INUM_COPY (3, optname, ioptname);
232
233 fd = SCM_FPORT_FDES (sock);
234 if (getsockopt (fd, ilevel, ioptname, (void *) optval, &optlen) == -1)
235 SCM_SYSERROR;
236
237 if (ilevel == SOL_SOCKET)
238 {
239 #ifdef SO_LINGER
240 if (ioptname == SO_LINGER)
241 {
242 #ifdef HAVE_STRUCT_LINGER
243 struct linger *ling = (struct linger *) optval;
244
245 return scm_cons (scm_long2num (ling->l_onoff),
246 scm_long2num (ling->l_linger));
247 #else
248 return scm_cons (scm_long2num (*(int *) optval)
249 SCM_MAKINUM (0));
250 #endif
251 }
252 else
253 #endif
254 if (0
255 #ifdef SO_SNDBUF
256 || ioptname == SO_SNDBUF
257 #endif
258 #ifdef SO_RCVBUF
259 || ioptname == SO_RCVBUF
260 #endif
261 )
262 {
263 return scm_long2num (*(scm_sizet *) optval);
264 }
265 }
266 return scm_long2num (*(int *) optval);
267 }
268 #undef FUNC_NAME
269
270 SCM_DEFINE (scm_setsockopt, "setsockopt", 4, 0, 0,
271 (SCM sock, SCM level, SCM optname, SCM value),
272 "Sets the value of a particular socket option for the socket\n"
273 "port @var{socket}. @var{level} is an integer code for type of option\n"
274 "being set, e.g., @code{SOL_SOCKET} for socket-level options.\n"
275 "@var{optname} is an\n"
276 "integer code for the option to set and should be specified using one of\n"
277 "the symbols @code{SO_DEBUG}, @code{SO_REUSEADDR} etc.\n"
278 "@var{value} is the value to which the option should be set. For\n"
279 "most options this must be an integer, but for @code{SO_LINGER} it must\n"
280 "be a pair.\n\n"
281 "The return value is unspecified.")
282 #define FUNC_NAME s_scm_setsockopt
283 {
284 int fd;
285 int optlen = -1;
286 /* size of optval is the largest supported option. */
287 #ifdef HAVE_STRUCT_LINGER
288 char optval[sizeof (struct linger)];
289 #else
290 char optval[sizeof (scm_sizet)];
291 #endif
292 int ilevel, ioptname;
293
294 sock = SCM_COERCE_OUTPORT (sock);
295
296 SCM_VALIDATE_OPFPORT (1, sock);
297 SCM_VALIDATE_INUM_COPY (2, level, ilevel);
298 SCM_VALIDATE_INUM_COPY (3, optname, ioptname);
299
300 fd = SCM_FPORT_FDES (sock);
301
302 if (ilevel == SOL_SOCKET)
303 {
304 #ifdef SO_LINGER
305 if (ioptname == SO_LINGER)
306 {
307 #ifdef HAVE_STRUCT_LINGER
308 struct linger ling;
309 long lv;
310
311 SCM_ASSERT (SCM_CONSP (value), value, SCM_ARG4, FUNC_NAME);
312 lv = SCM_NUM2LONG (4, SCM_CAR (value));
313 ling.l_onoff = (int) lv;
314 SCM_ASSERT_RANGE (SCM_ARG4, value, ling.l_onoff == lv);
315 lv = SCM_NUM2LONG (4, SCM_CDR (value));
316 ling.l_linger = (int) lv;
317 SCM_ASSERT_RANGE (SCM_ARG4, value, ling.l_linger == lv);
318 optlen = (int) sizeof (struct linger);
319 memcpy (optval, (void *) &ling, optlen);
320 #else
321 int ling;
322 long lv;
323
324 SCM_ASSERT (SCM_CONSP (value), value, SCM_ARG4, FUNC_NAME);
325 /* timeout is ignored, but may as well validate it. */
326 lv = SCM_NUM2LONG (4, SCM_CDR (value));
327 ling = (int) lv;
328 SCM_ASSERT_RANGE (SCM_ARG4, value, ling == lv);
329 lv = SCM_NUM2LONG (4, SCM_CAR (value));
330 ling = (int) lv;
331 SCM_ASSERT_RANGE (SCM_ARG4, value, ling == lv);
332 optlen = (int) sizeof (int);
333 (*(int *) optval) = ling;
334 #endif
335 }
336 else
337 #endif
338 if (0
339 #ifdef SO_SNDBUF
340 || ioptname == SO_SNDBUF
341 #endif
342 #ifdef SO_RCVBUF
343 || ioptname == SO_RCVBUF
344 #endif
345 )
346 {
347 long lv = SCM_NUM2LONG (4, value);
348
349 optlen = (int) sizeof (scm_sizet);
350 (*(scm_sizet *) optval) = (scm_sizet) lv;
351 }
352 }
353 if (optlen == -1)
354 {
355 /* Most options take an int. */
356 long lv = SCM_NUM2LONG (4, value);
357 int val = (int) lv;
358
359 SCM_ASSERT_RANGE (SCM_ARG4, value, val == lv);
360 optlen = (int) sizeof (int);
361 (*(int *) optval) = val;
362 }
363 if (setsockopt (fd, ilevel, ioptname, (void *) optval, optlen) == -1)
364 SCM_SYSERROR;
365 return SCM_UNSPECIFIED;
366 }
367 #undef FUNC_NAME
368
369 SCM_DEFINE (scm_shutdown, "shutdown", 2, 0, 0,
370 (SCM sock, SCM how),
371 "Sockets can be closed simply by using @code{close-port}. The\n"
372 "@code{shutdown} procedure allows reception or tranmission on a\n"
373 "connection to be shut down individually, according to the parameter\n"
374 "@var{how}:\n\n"
375 "@table @asis\n"
376 "@item 0\n"
377 "Stop receiving data for this socket. If further data arrives, reject it.\n"
378 "@item 1\n"
379 "Stop trying to transmit data from this socket. Discard any\n"
380 "data waiting to be sent. Stop looking for acknowledgement of\n"
381 "data already sent; don't retransmit it if it is lost.\n"
382 "@item 2\n"
383 "Stop both reception and transmission.\n"
384 "@end table\n\n"
385 "The return value is unspecified.")
386 #define FUNC_NAME s_scm_shutdown
387 {
388 int fd;
389 sock = SCM_COERCE_OUTPORT (sock);
390 SCM_VALIDATE_OPFPORT (1,sock);
391 SCM_VALIDATE_INUM (2,how);
392 SCM_ASSERT_RANGE(2,how,0 <= SCM_INUM (how) && 2 >= SCM_INUM (how));
393 fd = SCM_FPORT_FDES (sock);
394 if (shutdown (fd, SCM_INUM (how)) == -1)
395 SCM_SYSERROR;
396 return SCM_UNSPECIFIED;
397 }
398 #undef FUNC_NAME
399
400 /* convert fam/address/args into a sockaddr of the appropriate type.
401 args is modified by removing the arguments actually used.
402 which_arg and proc are used when reporting errors:
403 which_arg is the position of address in the original argument list.
404 proc is the name of the original procedure.
405 size returns the size of the structure allocated. */
406
407 static struct sockaddr *
408 scm_fill_sockaddr (int fam, SCM address, SCM *args, int which_arg,
409 const char *proc, int *size)
410 #define FUNC_NAME proc
411 {
412 switch (fam)
413 {
414 case AF_INET:
415 {
416 struct sockaddr_in *soka;
417 unsigned long addr;
418 int port;
419
420 SCM_VALIDATE_ULONG_COPY (which_arg, address, addr);
421 SCM_VALIDATE_CONS (which_arg + 1, *args);
422 SCM_VALIDATE_INUM_COPY (which_arg + 1, SCM_CAR (*args), port);
423 *args = SCM_CDR (*args);
424 soka = (struct sockaddr_in *) malloc (sizeof (struct sockaddr_in));
425 if (!soka)
426 scm_memory_error (proc);
427 /* 4.4BSD-style interface includes sin_len member and defines SIN_LEN,
428 4.3BSD does not. */
429 #ifdef SIN_LEN
430 soka->sin_len = sizeof (struct sockaddr_in);
431 #endif
432 soka->sin_family = AF_INET;
433 soka->sin_addr.s_addr = htonl (addr);
434 soka->sin_port = htons (port);
435 *size = sizeof (struct sockaddr_in);
436 return (struct sockaddr *) soka;
437 }
438 #ifdef AF_INET6
439 case AF_INET6:
440 {
441 /* see RFC2553. */
442 int port;
443 struct sockaddr_in6 *soka;
444 unsigned long flowinfo = 0;
445 unsigned long scope_id = 0;
446
447 if (SCM_INUMP (address))
448 SCM_ASSERT_RANGE (which_arg, address, SCM_INUM (address) >= 0);
449 else
450 {
451 SCM_VALIDATE_BIGINT (which_arg, address);
452 SCM_ASSERT_RANGE (which_arg, address,
453 !SCM_BIGSIGN (address)
454 && (SCM_BITSPERDIG
455 * SCM_NUMDIGS (address) <= 128));
456 }
457 SCM_VALIDATE_CONS (which_arg + 1, *args);
458 SCM_VALIDATE_INUM_COPY (which_arg + 1, SCM_CAR (*args), port);
459 *args = SCM_CDR (*args);
460 if (SCM_CONSP (*args))
461 {
462 SCM_VALIDATE_ULONG_COPY (which_arg + 2, SCM_CAR (*args), flowinfo);
463 *args = SCM_CDR (*args);
464 if (SCM_CONSP (*args))
465 {
466 SCM_VALIDATE_ULONG_COPY (which_arg + 3, SCM_CAR (*args),
467 scope_id);
468 *args = SCM_CDR (*args);
469 }
470 }
471 soka = (struct sockaddr_in6 *) malloc (sizeof (struct sockaddr_in6));
472 if (!soka)
473 scm_memory_error (proc);
474 #ifdef SIN_LEN6
475 soka->sin6_len = sizeof (struct sockaddr_in6);
476 #endif
477 soka->sin6_family = AF_INET6;
478 if (SCM_INUMP (address))
479 {
480 uint32_t addr = htonl (SCM_INUM (address));
481
482 memset (soka->sin6_addr.s6_addr, 0, 12);
483 memcpy (soka->sin6_addr.s6_addr + 12, &addr, 4);
484 }
485 else
486 {
487 scm_sizet i;
488
489 memset (soka->sin6_addr.s6_addr, 0, 16);
490 memcpy (soka->sin6_addr.s6_addr, SCM_BDIGITS (address),
491 SCM_NUMDIGS (address) * (SCM_BITSPERDIG / 8));
492 #ifndef WORDS_BIGENDIAN
493 /* flip to network order. */
494 for (i = 0; i < 8; i++)
495 {
496 char c = soka->sin6_addr.s6_addr[i];
497
498 soka->sin6_addr.s6_addr[i] = soka->sin6_addr.s6_addr[15 - i];
499 soka->sin6_addr.s6_addr[15 - i] = c;
500 }
501 #endif
502 }
503 soka->sin6_port = htons (port);
504 soka->sin6_flowinfo = flowinfo;
505 #ifdef HAVE_SIN6_SCOPE_ID
506 soka->sin6_scope_id = scope_id;
507 #endif
508 *size = sizeof (struct sockaddr_in6);
509 return (struct sockaddr *) soka;
510 }
511 #endif
512 #ifdef HAVE_UNIX_DOMAIN_SOCKETS
513 case AF_UNIX:
514 {
515 struct sockaddr_un *soka;
516 int addr_size;
517
518 SCM_ASSERT (SCM_STRINGP (address), address, which_arg, proc);
519 /* the static buffer size in sockaddr_un seems to be arbitrary
520 and not necessarily a hard limit. e.g., the glibc manual
521 suggests it may be possible to declare it size 0. let's
522 ignore it. if the O/S doesn't like the size it will cause
523 connect/bind etc., to fail. sun_path is always the last
524 member of the structure. */
525 addr_size = sizeof (struct sockaddr_un)
526 + max (0, SCM_STRING_LENGTH (address) + 1 - (sizeof soka->sun_path));
527 soka = (struct sockaddr_un *) malloc (addr_size);
528 if (!soka)
529 scm_memory_error (proc);
530 memset (soka, 0, addr_size); /* for sun_len: see sin_len above. */
531 soka->sun_family = AF_UNIX;
532 memcpy (soka->sun_path, SCM_STRING_CHARS (address),
533 SCM_STRING_LENGTH (address));
534 *size = SUN_LEN (soka);
535 return (struct sockaddr *) soka;
536 }
537 #endif
538 default:
539 scm_out_of_range (proc, SCM_MAKINUM (fam));
540 }
541 }
542 #undef FUNC_NAME
543
544 SCM_DEFINE (scm_connect, "connect", 3, 0, 1,
545 (SCM sock, SCM fam, SCM address, SCM args),
546 "Initiates a connection from a socket using a specified address\n"
547 "family to the address\n"
548 "specified by @var{address} and possibly @var{args}.\n"
549 "The format required for @var{address}\n"
550 "and @var{args} depends on the family of the socket.\n\n"
551 "For a socket of family @code{AF_UNIX},\n"
552 "only @var{address} is specified and must be a string with the\n"
553 "filename where the socket is to be created.\n\n"
554 "For a socket of family @code{AF_INET},\n"
555 "@var{address} must be an integer IPv4 host address and\n"
556 "@var{args} must be a single integer port number.\n\n"
557 "For a socket of family @code{AF_INET6},\n"
558 "@var{address} must be an integer IPv6 host address and\n"
559 "@var{args} may be up to three integers:\n"
560 "port [flowinfo] [scope_id],\n"
561 "where flowinfo and scope_id default to zero.\n\n"
562 "The return value is unspecified.")
563 #define FUNC_NAME s_scm_connect
564 {
565 int fd;
566 struct sockaddr *soka;
567 int size;
568
569 sock = SCM_COERCE_OUTPORT (sock);
570 SCM_VALIDATE_OPFPORT (1,sock);
571 SCM_VALIDATE_INUM (2,fam);
572 fd = SCM_FPORT_FDES (sock);
573 soka = scm_fill_sockaddr (SCM_INUM (fam), address, &args, 3, FUNC_NAME,
574 &size);
575 if (connect (fd, soka, size) == -1)
576 {
577 int save_errno = errno;
578
579 free (soka);
580 errno = save_errno;
581 SCM_SYSERROR;
582 }
583 free (soka);
584 return SCM_UNSPECIFIED;
585 }
586 #undef FUNC_NAME
587
588 SCM_DEFINE (scm_bind, "bind", 3, 0, 1,
589 (SCM sock, SCM fam, SCM address, SCM args),
590 "Assigns an address to the socket port @var{socket}.\n"
591 "Generally this only needs to be done for server sockets,\n"
592 "so they know where to look for incoming connections. A socket\n"
593 "without an address will be assigned one automatically when it\n"
594 "starts communicating.\n\n"
595 "The format of @var{address} and @var{ARG} @dots{} depends on the family\n"
596 "of the socket.\n\n"
597 "For a socket of family @code{AF_UNIX}, only @var{address}\n"
598 "is specified and must \n"
599 "be a string with the filename where the socket is to be created.\n\n"
600 "For a socket of family @code{AF_INET}, @var{address} must be an integer\n"
601 "Internet host address and @var{arg} @dots{} must be a single integer\n"
602 "port number.\n\n"
603 "The values of the following variables can also be used for @var{address}:\n\n"
604 "@defvar INADDR_ANY\n"
605 "Allow connections from any address.\n"
606 "@end defvar\n\n"
607 "@defvar INADDR_LOOPBACK\n"
608 "The address of the local host using the loopback device.\n"
609 "@end defvar\n\n"
610 "@defvar INADDR_BROADCAST\n"
611 "The broadcast address on the local network.\n"
612 "@end defvar\n\n"
613 "@defvar INADDR_NONE\n"
614 "No address.\n"
615 "@end defvar\n\n"
616 "The return value is unspecified.")
617 #define FUNC_NAME s_scm_bind
618 {
619 struct sockaddr *soka;
620 int size;
621 int fd;
622
623 sock = SCM_COERCE_OUTPORT (sock);
624 SCM_VALIDATE_OPFPORT (1, sock);
625 SCM_VALIDATE_INUM (2, fam);
626 soka = scm_fill_sockaddr (SCM_INUM (fam), address, &args, 3, FUNC_NAME,
627 &size);
628 fd = SCM_FPORT_FDES (sock);
629 if (bind (fd, soka, size) == -1)
630 {
631 int save_errno = errno;
632
633 free (soka);
634 errno = save_errno;
635 SCM_SYSERROR;
636 }
637 free (soka);
638 return SCM_UNSPECIFIED;
639 }
640 #undef FUNC_NAME
641
642 SCM_DEFINE (scm_listen, "listen", 2, 0, 0,
643 (SCM sock, SCM backlog),
644 "This procedure enables @var{socket} to accept connection\n"
645 "requests. @var{backlog} is an integer specifying\n"
646 "the maximum length of the queue for pending connections.\n"
647 "If the queue fills, new clients will fail to connect until the\n"
648 "server calls @code{accept} to accept a connection from the queue.\n\n"
649 "The return value is unspecified.")
650 #define FUNC_NAME s_scm_listen
651 {
652 int fd;
653 sock = SCM_COERCE_OUTPORT (sock);
654 SCM_VALIDATE_OPFPORT (1,sock);
655 SCM_VALIDATE_INUM (2,backlog);
656 fd = SCM_FPORT_FDES (sock);
657 if (listen (fd, SCM_INUM (backlog)) == -1)
658 SCM_SYSERROR;
659 return SCM_UNSPECIFIED;
660 }
661 #undef FUNC_NAME
662
663 /* Put the components of a sockaddr into a new SCM vector. */
664 static SCM
665 scm_addr_vector (struct sockaddr *address, const char *proc)
666 {
667 short int fam = address->sa_family;
668 SCM result;
669 SCM *ve;
670
671 switch (fam)
672 {
673 case AF_INET:
674 {
675 struct sockaddr_in *nad = (struct sockaddr_in *) address;
676
677 result = scm_c_make_vector (3, SCM_UNSPECIFIED);
678 ve = SCM_VELTS (result);
679 ve[0] = scm_ulong2num ((unsigned long) fam);
680 ve[1] = scm_ulong2num (ntohl (nad->sin_addr.s_addr));
681 ve[2] = scm_ulong2num ((unsigned long) ntohs (nad->sin_port));
682 }
683 break;
684 #ifdef AF_INET6
685 case AF_INET6:
686 {
687 struct sockaddr_in6 *nad = (struct sockaddr_in6 *) address;
688
689 result = scm_c_make_vector (5, SCM_UNSPECIFIED);
690 ve = SCM_VELTS (result);
691 ve[0] = scm_ulong2num ((unsigned long) fam);
692 /* FIXME */
693 ve[1] = SCM_INUM0;
694 ve[2] = scm_ulong2num ((unsigned long) ntohs (nad->sin6_port));
695 ve[3] = scm_ulong2num ((unsigned long) nad->sin6_flowinfo);
696 #ifdef HAVE_SIN6_SCOPE_ID
697 ve[4] = scm_ulong2num ((unsigned long) nad->sin6_scope_id);
698 #else
699 ve[4] = SCM_INUM0;
700 #endif
701 }
702 break;
703 #endif
704 #ifdef HAVE_UNIX_DOMAIN_SOCKETS
705 case AF_UNIX:
706 {
707 struct sockaddr_un *nad = (struct sockaddr_un *) address;
708
709 result = scm_c_make_vector (2, SCM_UNSPECIFIED);
710 ve = SCM_VELTS (result);
711 ve[0] = scm_ulong2num ((unsigned long) fam);
712 ve[1] = scm_makfromstr (nad->sun_path,
713 (scm_sizet) strlen (nad->sun_path), 0);
714 }
715 break;
716 #endif
717 default:
718 scm_misc_error (proc, "Unrecognised address family: ~A",
719 SCM_LIST1 (SCM_MAKINUM (fam)));
720 }
721 return result;
722 }
723
724 /* calculate the size of a buffer large enough to hold any supported
725 sockaddr type. if the buffer isn't large enough, certain system
726 calls will return a truncated address. */
727
728 #if defined (HAVE_UNIX_DOMAIN_SOCKETS)
729 #define MAX_SIZE_UN sizeof (struct sockaddr_un)
730 #else
731 #define MAX_SIZE_UN 0
732 #endif
733
734 #if defined (AF_INET6)
735 #define MAX_SIZE_IN6 sizeof (struct sockaddr_in6)
736 #else
737 #define MAX_SIZE_IN6 0
738 #endif
739
740 #define MAX_ADDR_SIZE max (max (sizeof (struct sockaddr_in), MAX_SIZE_IN6),\
741 MAX_SIZE_UN)
742
743 SCM_DEFINE (scm_accept, "accept", 1, 0, 0,
744 (SCM sock),
745 "Accepts a connection on a bound, listening socket @var{socket}. If there\n"
746 "are no pending connections in the queue, it waits until\n"
747 "one is available unless the non-blocking option has been set on the\n"
748 "socket.\n\n"
749 "The return value is a\n"
750 "pair in which the CAR is a new socket port for the connection and\n"
751 "the CDR is an object with address information about the client which\n"
752 "initiated the connection.\n\n"
753 "If the address is not available then the CDR will be an empty vector.\n\n"
754 "@var{socket} does not become part of the\n"
755 "connection and will continue to accept new requests.")
756 #define FUNC_NAME s_scm_accept
757 {
758 int fd;
759 int newfd;
760 SCM address;
761 SCM newsock;
762 int addr_size = MAX_ADDR_SIZE;
763 char max_addr[MAX_ADDR_SIZE];
764 struct sockaddr *addr = (struct sockaddr *) max_addr;
765
766 sock = SCM_COERCE_OUTPORT (sock);
767 SCM_VALIDATE_OPFPORT (1, sock);
768 fd = SCM_FPORT_FDES (sock);
769 newfd = accept (fd, addr, &addr_size);
770 if (newfd == -1)
771 SCM_SYSERROR;
772 newsock = SCM_SOCK_FD_TO_PORT (newfd);
773 if (addr_size > 0)
774 address = scm_addr_vector (addr, FUNC_NAME);
775 else
776 address = SCM_BOOL_F;
777
778 return scm_cons (newsock, address);
779 }
780 #undef FUNC_NAME
781
782 SCM_DEFINE (scm_getsockname, "getsockname", 1, 0, 0,
783 (SCM sock),
784 "Return the address of @var{socket}, in the same form as the\n"
785 "object returned by @code{accept}. On many systems the address\n"
786 "of a socket in the @code{AF_FILE} namespace cannot be read.")
787 #define FUNC_NAME s_scm_getsockname
788 {
789 int fd;
790 SCM result;
791 int addr_size = MAX_ADDR_SIZE;
792 char max_addr[MAX_ADDR_SIZE];
793 struct sockaddr *addr = (struct sockaddr *) max_addr;
794
795 sock = SCM_COERCE_OUTPORT (sock);
796 SCM_VALIDATE_OPFPORT (1,sock);
797 fd = SCM_FPORT_FDES (sock);
798 if (getsockname (fd, addr, &addr_size) == -1)
799 SCM_SYSERROR;
800 if (addr_size > 0)
801 result = scm_addr_vector (addr, FUNC_NAME);
802 else
803 result = SCM_BOOL_F;
804 return result;
805 }
806 #undef FUNC_NAME
807
808 SCM_DEFINE (scm_getpeername, "getpeername", 1, 0, 0,
809 (SCM sock),
810 "Return the address of the socket that the socket @var{socket}\n"
811 "is connected to, in the same form as the object returned by\n"
812 "@code{accept}. On many systems the address of a socket in the\n"
813 "@code{AF_FILE} namespace cannot be read.")
814 #define FUNC_NAME s_scm_getpeername
815 {
816 int fd;
817 SCM result;
818 int addr_size = MAX_ADDR_SIZE;
819 char max_addr[MAX_ADDR_SIZE];
820 struct sockaddr *addr = (struct sockaddr *) max_addr;
821
822 sock = SCM_COERCE_OUTPORT (sock);
823 SCM_VALIDATE_OPFPORT (1,sock);
824 fd = SCM_FPORT_FDES (sock);
825 if (getpeername (fd, addr, &addr_size) == -1)
826 SCM_SYSERROR;
827 if (addr_size > 0)
828 result = scm_addr_vector (addr, FUNC_NAME);
829 else
830 result = SCM_BOOL_F;
831 return result;
832 }
833 #undef FUNC_NAME
834
835 SCM_DEFINE (scm_recv, "recv!", 2, 1, 0,
836 (SCM sock, SCM buf, SCM flags),
837 "Receives data from the socket port @var{socket}. @var{socket} must already\n"
838 "be bound to the address from which data is to be received.\n"
839 "@var{buf} is a string into which\n"
840 "the data will be written. The size of @var{buf} limits the amount of\n"
841 "data which can be received: in the case of packet\n"
842 "protocols, if a packet larger than this limit is encountered then some data\n"
843 "will be irrevocably lost.\n\n"
844 "The optional @var{flags} argument is a value or\n"
845 "bitwise OR of MSG_OOB, MSG_PEEK, MSG_DONTROUTE etc.\n\n"
846 "The value returned is the number of bytes read from the socket.\n\n"
847 "Note that the data is read directly from the socket file descriptor:\n"
848 "any unread buffered port data is ignored.")
849 #define FUNC_NAME s_scm_recv
850 {
851 int rv;
852 int fd;
853 int flg;
854
855 SCM_VALIDATE_OPFPORT (1,sock);
856 SCM_VALIDATE_STRING (2,buf);
857 SCM_VALIDATE_INUM_DEF_COPY (3,flags,0,flg);
858 fd = SCM_FPORT_FDES (sock);
859
860 SCM_SYSCALL (rv = recv (fd, SCM_STRING_CHARS (buf), SCM_STRING_LENGTH (buf), flg));
861 if (rv == -1)
862 SCM_SYSERROR;
863
864 return SCM_MAKINUM (rv);
865 }
866 #undef FUNC_NAME
867
868 SCM_DEFINE (scm_send, "send", 2, 1, 0,
869 (SCM sock, SCM message, SCM flags),
870 "Transmits the string @var{message} on the socket port @var{socket}. \n"
871 "@var{socket} must already be bound to a destination address. The\n"
872 "value returned is the number of bytes transmitted -- it's possible for\n"
873 "this to be less than the length of @var{message} if the socket is\n"
874 "set to be non-blocking. The optional @var{flags} argument is a value or\n"
875 "bitwise OR of MSG_OOB, MSG_PEEK, MSG_DONTROUTE etc.\n\n"
876 "Note that the data is written directly to the socket file descriptor:\n"
877 "any unflushed buffered port data is ignored.")
878 #define FUNC_NAME s_scm_send
879 {
880 int rv;
881 int fd;
882 int flg;
883
884 sock = SCM_COERCE_OUTPORT (sock);
885 SCM_VALIDATE_OPFPORT (1,sock);
886 SCM_VALIDATE_STRING (2, message);
887 SCM_VALIDATE_INUM_DEF_COPY (3,flags,0,flg);
888 fd = SCM_FPORT_FDES (sock);
889
890 SCM_SYSCALL (rv = send (fd, SCM_STRING_CHARS (message), SCM_STRING_LENGTH (message), flg));
891 if (rv == -1)
892 SCM_SYSERROR;
893 return SCM_MAKINUM (rv);
894 }
895 #undef FUNC_NAME
896
897 SCM_DEFINE (scm_recvfrom, "recvfrom!", 2, 3, 0,
898 (SCM sock, SCM str, SCM flags, SCM start, SCM end),
899 "Return data from the socket port @var{socket} and also\n"
900 "information about where the data was received from.\n"
901 "@var{socket} must already be bound to the address from which\n"
902 "data is to be received. @code{str}, is a string into which the\n"
903 "data will be written. The size of @var{str} limits the amount\n"
904 "of data which can be received: in the case of packet protocols,\n"
905 "if a packet larger than this limit is encountered then some\n"
906 "data will be irrevocably lost.\n"
907 "\n"
908 "The optional @var{flags} argument is a value or bitwise OR of\n"
909 "@code{MSG_OOB}, @code{MSG_PEEK}, @code{MSG_DONTROUTE} etc.\n"
910 "\n"
911 "The value returned is a pair: the @emph{car} is the number of\n"
912 "bytes read from the socket and the @emph{cdr} an address object\n"
913 "in the same form as returned by @code{accept}.\n"
914 "\n"
915 "The @var{start} and @var{end} arguments specify a substring of\n"
916 "@var{str} to which the data should be written.\n"
917 "\n"
918 "Note that the data is read directly from the socket file\n"
919 "descriptor: any unread buffered port data is ignored.")
920 #define FUNC_NAME s_scm_recvfrom
921 {
922 int rv;
923 int fd;
924 int flg;
925 char *buf;
926 int offset;
927 int cend;
928 SCM address;
929 int addr_size = MAX_ADDR_SIZE;
930 char max_addr[MAX_ADDR_SIZE];
931 struct sockaddr *addr = (struct sockaddr *) max_addr;
932
933 SCM_VALIDATE_OPFPORT (1,sock);
934 fd = SCM_FPORT_FDES (sock);
935 SCM_VALIDATE_SUBSTRING_SPEC_COPY (2, str, buf, 4, start, offset,
936 5, end, cend);
937 if (SCM_UNBNDP (flags))
938 flg = 0;
939 else
940 SCM_VALIDATE_ULONG_COPY (3, flags, flg);
941
942 /* recvfrom will not necessarily return an address. usually nothing
943 is returned for stream sockets. */
944 addr->sa_family = AF_UNSPEC;
945 SCM_SYSCALL (rv = recvfrom (fd, buf + offset,
946 cend - offset, flg,
947 addr, &addr_size));
948 if (rv == -1)
949 SCM_SYSERROR;
950 if (addr_size > 0 && addr->sa_family != AF_UNSPEC)
951 address = scm_addr_vector (addr, FUNC_NAME);
952 else
953 address = SCM_BOOL_F;
954
955 return scm_cons (SCM_MAKINUM (rv), address);
956 }
957 #undef FUNC_NAME
958
959 SCM_DEFINE (scm_sendto, "sendto", 4, 0, 1,
960 (SCM sock, SCM message, SCM fam, SCM address, SCM args_and_flags),
961 "Transmits the string @var{message} on the socket port @var{socket}. The\n"
962 "destination address is specified using the @var{family}, @var{address} and\n"
963 "@var{arg} arguments, in a similar way to the @code{connect}\n"
964 "procedure. The\n"
965 "value returned is the number of bytes transmitted -- it's possible for\n"
966 "this to be less than the length of @var{message} if the socket is\n"
967 "set to be non-blocking. The optional @var{flags} argument is a value or\n"
968 "bitwise OR of MSG_OOB, MSG_PEEK, MSG_DONTROUTE etc.\n\n"
969 "Note that the data is written directly to the socket file descriptor:\n"
970 "any unflushed buffered port data is ignored.")
971 #define FUNC_NAME s_scm_sendto
972 {
973 int rv;
974 int fd;
975 int flg;
976 struct sockaddr *soka;
977 int size;
978
979 sock = SCM_COERCE_OUTPORT (sock);
980 SCM_VALIDATE_FPORT (1,sock);
981 SCM_VALIDATE_STRING (2, message);
982 SCM_VALIDATE_INUM (3,fam);
983 fd = SCM_FPORT_FDES (sock);
984 soka = scm_fill_sockaddr (SCM_INUM (fam), address, &args_and_flags, 4,
985 FUNC_NAME, &size);
986 if (SCM_NULLP (args_and_flags))
987 flg = 0;
988 else
989 {
990 SCM_VALIDATE_CONS (5,args_and_flags);
991 flg = SCM_NUM2ULONG (5, SCM_CAR (args_and_flags));
992 }
993 SCM_SYSCALL (rv = sendto (fd, SCM_STRING_CHARS (message),
994 SCM_STRING_LENGTH (message),
995 flg, soka, size));
996 if (rv == -1)
997 {
998 int save_errno = errno;
999 free (soka);
1000 errno = save_errno;
1001 SCM_SYSERROR;
1002 }
1003 free (soka);
1004 return SCM_MAKINUM (rv);
1005 }
1006 #undef FUNC_NAME
1007 \f
1008
1009
1010 void
1011 scm_init_socket ()
1012 {
1013 /* protocol families. */
1014 #ifdef AF_UNSPEC
1015 scm_sysintern ("AF_UNSPEC", SCM_MAKINUM (AF_UNSPEC));
1016 #endif
1017 #ifdef AF_UNIX
1018 scm_sysintern ("AF_UNIX", SCM_MAKINUM (AF_UNIX));
1019 #endif
1020 #ifdef AF_INET
1021 scm_sysintern ("AF_INET", SCM_MAKINUM (AF_INET));
1022 #endif
1023 #ifdef AF_INET6
1024 scm_sysintern ("AF_INET6", SCM_MAKINUM (AF_INET6));
1025 #endif
1026
1027 #ifdef PF_UNSPEC
1028 scm_sysintern ("PF_UNSPEC", SCM_MAKINUM (PF_UNSPEC));
1029 #endif
1030 #ifdef PF_UNIX
1031 scm_sysintern ("PF_UNIX", SCM_MAKINUM (PF_UNIX));
1032 #endif
1033 #ifdef PF_INET
1034 scm_sysintern ("PF_INET", SCM_MAKINUM (PF_INET));
1035 #endif
1036 #ifdef PF_INET6
1037 scm_sysintern ("PF_INET6", SCM_MAKINUM (PF_INET6));
1038 #endif
1039
1040 /* socket types. */
1041 #ifdef SOCK_STREAM
1042 scm_sysintern ("SOCK_STREAM", SCM_MAKINUM (SOCK_STREAM));
1043 #endif
1044 #ifdef SOCK_DGRAM
1045 scm_sysintern ("SOCK_DGRAM", SCM_MAKINUM (SOCK_DGRAM));
1046 #endif
1047 #ifdef SOCK_RAW
1048 scm_sysintern ("SOCK_RAW", SCM_MAKINUM (SOCK_RAW));
1049 #endif
1050
1051 /* setsockopt level. */
1052 #ifdef SOL_SOCKET
1053 scm_sysintern ("SOL_SOCKET", SCM_MAKINUM (SOL_SOCKET));
1054 #endif
1055 #ifdef SOL_IP
1056 scm_sysintern ("SOL_IP", SCM_MAKINUM (SOL_IP));
1057 #endif
1058 #ifdef SOL_TCP
1059 scm_sysintern ("SOL_TCP", SCM_MAKINUM (SOL_TCP));
1060 #endif
1061 #ifdef SOL_UDP
1062 scm_sysintern ("SOL_UDP", SCM_MAKINUM (SOL_UDP));
1063 #endif
1064
1065 /* setsockopt names. */
1066 #ifdef SO_DEBUG
1067 scm_sysintern ("SO_DEBUG", SCM_MAKINUM (SO_DEBUG));
1068 #endif
1069 #ifdef SO_REUSEADDR
1070 scm_sysintern ("SO_REUSEADDR", SCM_MAKINUM (SO_REUSEADDR));
1071 #endif
1072 #ifdef SO_STYLE
1073 scm_sysintern ("SO_STYLE", SCM_MAKINUM (SO_STYLE));
1074 #endif
1075 #ifdef SO_TYPE
1076 scm_sysintern ("SO_TYPE", SCM_MAKINUM (SO_TYPE));
1077 #endif
1078 #ifdef SO_ERROR
1079 scm_sysintern ("SO_ERROR", SCM_MAKINUM (SO_ERROR));
1080 #endif
1081 #ifdef SO_DONTROUTE
1082 scm_sysintern ("SO_DONTROUTE", SCM_MAKINUM (SO_DONTROUTE));
1083 #endif
1084 #ifdef SO_BROADCAST
1085 scm_sysintern ("SO_BROADCAST", SCM_MAKINUM (SO_BROADCAST));
1086 #endif
1087 #ifdef SO_SNDBUF
1088 scm_sysintern ("SO_SNDBUF", SCM_MAKINUM (SO_SNDBUF));
1089 #endif
1090 #ifdef SO_RCVBUF
1091 scm_sysintern ("SO_RCVBUF", SCM_MAKINUM (SO_RCVBUF));
1092 #endif
1093 #ifdef SO_KEEPALIVE
1094 scm_sysintern ("SO_KEEPALIVE", SCM_MAKINUM (SO_KEEPALIVE));
1095 #endif
1096 #ifdef SO_OOBINLINE
1097 scm_sysintern ("SO_OOBINLINE", SCM_MAKINUM (SO_OOBINLINE));
1098 #endif
1099 #ifdef SO_NO_CHECK
1100 scm_sysintern ("SO_NO_CHECK", SCM_MAKINUM (SO_NO_CHECK));
1101 #endif
1102 #ifdef SO_PRIORITY
1103 scm_sysintern ("SO_PRIORITY", SCM_MAKINUM (SO_PRIORITY));
1104 #endif
1105 #ifdef SO_LINGER
1106 scm_sysintern ("SO_LINGER", SCM_MAKINUM (SO_LINGER));
1107 #endif
1108
1109 /* recv/send options. */
1110 #ifdef MSG_OOB
1111 scm_sysintern ("MSG_OOB", SCM_MAKINUM (MSG_OOB));
1112 #endif
1113 #ifdef MSG_PEEK
1114 scm_sysintern ("MSG_PEEK", SCM_MAKINUM (MSG_PEEK));
1115 #endif
1116 #ifdef MSG_DONTROUTE
1117 scm_sysintern ("MSG_DONTROUTE", SCM_MAKINUM (MSG_DONTROUTE));
1118 #endif
1119
1120 scm_add_feature ("socket");
1121
1122 #ifndef SCM_MAGIC_SNARFER
1123 #include "libguile/socket.x"
1124 #endif
1125 }
1126
1127
1128 /*
1129 Local Variables:
1130 c-file-style: "gnu"
1131 End:
1132 */