1 /*
2  * Copyright (c) 1997, 1998, 1999, 2000, 2001, 2002, 2004, 2005, 2008, 2009,
3  *               2010, 2011, 2012, 2013, 2016, 2017
4  *      Inferno Nettverk A/S, Norway.  All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  * 1. The above copyright notice, this list of conditions and the following
10  *    disclaimer must appear in all copies of the software, derivative works
11  *    or modified versions, and any portions thereof, aswell as in all
12  *    supporting documentation.
13  * 2. All advertising materials mentioning features or use of this software
14  *    must display the following acknowledgement:
15  *      This product includes software developed by
16  *      Inferno Nettverk A/S, Norway.
17  * 3. The name of the author may not be used to endorse or promote products
18  *    derived from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
21  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
22  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
23  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
24  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
25  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30  *
31  * Inferno Nettverk A/S requests users of this software to return to
32  *
33  *  Software Distribution Coordinator  or  sdc@inet.no
34  *  Inferno Nettverk A/S
35  *  Oslo Research Park
36  *  Gaustadall�en 21
37  *  NO-0349 Oslo
38  *  Norway
39  *
40  * any improvements or extensions that they make and grant Inferno Nettverk A/S
41  * the rights to redistribute these changes.
42  *
43  */
44 
45 /* $Id: socks.h,v 1.287.6.6 2017/01/31 14:35:55 karls Exp $ */
46 
47 #ifndef _SOCKS_H_
48 #define _SOCKS_H_
49 
50 #define HAVE_SOCKS_RULES                  (0)
51 
52 #ifndef HAVE_OSF_OLDSTYLE
53 #define HAVE_OSF_OLDSTYLE 0
54 #endif /* !HAVE_OSF_OLDSTYLE */
55 
56 #if SOCKSLIBRARY_DYNAMIC
57 
58 #ifdef __COVERITY__
59 /*
60  * Coverity naturally has no idea what the function sys_foo calls does,
61  * so let it pretend sys_foo is the same as foo.
62  * Means Coverity can't catch errors in the code around the call to
63  * sys_foo(), but avoids dozens of false positives because Coverity has no
64  * idea what the dlopen(3)-ed functions do.
65  */
66 #define sys_accept accept
67 #define sys_bind bind
68 #define sys_bindresvport bindresvport
69 #define sys_connect connect
70 #define sys_gethostbyname gethostbyname
71 #define sys_gethostbyname2 gethostbyname2
72 #define sys_getaddrinfo getaddrinfo
73 #define sys_getipnodebyname getipnodebyname
74 #define sys_getpeername getpeername
75 #define sys_getsockname getsockname
76 #define sys_getsockopt getsockopt
77 #define sys_listen listen
78 #define sys_read read
79 #define sys_readv readv
80 #define sys_recv recv
81 #define sys_recvfrom recvfrom
82 #define sys_recvfrom recvfrom
83 #define sys_recvmsg recvmsg
84 #define sys_rresvport rresvport
85 #define sys_send send
86 #define sys_sendmsg sendmsg
87 #define sys_sendto sendto
88 #define sys_write write
89 #define sys_writev writev
90 #endif /* __COVERITY__ */
91 
92 
93 #if 0 /* XXX disable until testing on AIX/other can be done */
94 
95 /* XXX needed on AIX apparently */
96 #ifdef recvmsg
97 #define recvmsg_system recvmsg
98 #undef recvmsg
99 #endif /* recvmsg */
100 
101 #if HAVE_SYSTEM_XMSG_MAGIC
102 #undef recvmsg_system
103 #define recvmsg_system nrecvmsg
104 #endif /* HAVE_SYSTEM_XMSG_MAGIC */
105 
106 #ifdef sendmsg
107 #define sendmsg_system sendmsg
108 #undef sendmsg
109 #endif /* sendmsg */
110 
111 #if HAVE_SYSTEM_XMSG_MAGIC
112 #undef sendmsg_system
113 #define sendmsg_system nsendmsg
114 #endif /* HAVE_SYSTEM_XMSG_MAGIC */
115 #endif
116 
117 #ifdef accept
118 #undef accept
119 #endif /* accept */
120 #if HAVE_EXTRA_OSF_SYMBOLS
121 #define accept(s, addr, addrlen)         sys_Eaccept(s, addr, addrlen)
122 #else
123 #define accept(s, addr, addrlen)         sys_accept(s, addr, addrlen)
124 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
125 
126 #ifdef bind
127 #undef bind
128 #endif /* bind */
129 #if (defined __sun) && (defined _XPG4_2)
130 #define bind(s, name, namelen)         sys_xnet_bind(s, name, namelen)
131 #else
132 #define bind(s, name, namelen)         sys_bind(s, name, namelen)
133 #endif
134 
135 #ifdef bindresvport
136 #undef bindresvport
137 #endif /* bindresvport */
138 #define bindresvport(sd, sin)            sys_bindresvport(sd, sin)
139 
140 #ifdef connect
141 #undef connect
142 #endif /* connect */
143 #if (defined __sun) && (defined _XPG4_2)
144 #define connect(s, name, namelen)      sys_xnet_connect(s, name, namelen)
145 #else
146 #define connect(s, name, namelen)      sys_connect(s, name, namelen)
147 #endif
148 
149 
150 #ifdef gethostbyname
151 #undef gethostbyname
152 #endif /* gethostbyname */
153 
154 #if HAVE_GETHOSTBYNAME2
155 
156 /*
157  * a little tricky ... we need it to be at the bottom of the stack,
158  * like a syscall.
159  */
160 #define gethostbyname(name)            sys_gethostbyname2(name, AF_INET)
161 #else
162 #define gethostbyname(name)            sys_gethostbyname(name)
163 
164 #endif /* HAVE_GETHOSTBYNAME2 */
165 
166 #ifdef gethostbyname2
167 #undef gethostbyname2
168 #endif /* gethostbyname2 */
169 #define gethostbyname2(name, af)       sys_gethostbyname2(name, af)
170 
171 #ifdef getaddrinfo
172 #undef getaddrinfo
173 #endif /* getaddrinfo */
174 #define getaddrinfo(nodename, servname, hints, res)   \
175          sys_getaddrinfo(nodename, servname, hints, res)
176 
177 #ifdef getipnodebyname
178 #undef getipnodebyname
179 #endif /* getipnodebyname */
180 #define getipnodebyname(name, af, flags, error_num)   \
181          sys_getipnodebyname(name, af, flags, error_num)
182 
183 #ifdef freehostent
184 #undef freehostent
185 #endif /* freehostent */
186 #define freehostent(ptr)            sys_freehostent(ptr)
187 
188 #if HAVE_GETNAMEINFO
189 
190 #define getnameinfo(sa, salen, host, hostlen, serv, servlen, flags) \
191          sys_getnameinfo(sa, salen, host, hostlen, serv, servlen, flags)
192 
193 #endif /* HAVE_GETNAMEINFO  */
194 
195 
196 #ifdef getpeername
197 #undef getpeername
198 #endif /* getpeername */
199 
200 #if HAVE_EXTRA_OSF_SYMBOLS
201 #define getpeername(s, name, namelen)   sys_Egetpeername(s, name, namelen)
202 #else
203 #define getpeername(s, name, namelen)   sys_getpeername(s, name, namelen)
204 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
205 
206 #ifdef getsockname
207 #undef getsockname
208 #endif /* getsockname */
209 #if HAVE_EXTRA_OSF_SYMBOLS
210 #define getsockname(s, name, namelen)   sys_Egetsockname(s, name, namelen)
211 #else
212 #define getsockname(s, name, namelen)   sys_getsockname(s, name, namelen)
213 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
214 
215 #ifdef getsockopt
216 #undef getsockopt
217 #endif /* getsockopt */
218 #if HAVE_EXTRA_OSF_SYMBOLS
219 #define getsockopt(a, b, c, d, e) sys_Egetsockopt(a, b, c, d, e)
220 #else
221 #define getsockopt(a, b, c, d, e) sys_getsockopt(a, b, c, d, e)
222 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
223 
224 #ifdef listen
225 #undef listen
226 #endif /* listen */
227 #if (defined __sun) && (defined _XPG4_2)
228 #define listen(s, backlog)   sys_xnet_listen(s, backlog)
229 #else
230 #define listen(s, backlog)   sys_listen(s, backlog)
231 #endif
232 
233 #ifdef read
234 #undef read
235 #endif /* read */
236 #define read(d, buf, nbytes)            sys_read(d, buf, nbytes)
237 
238 #ifdef readv
239 #undef readv
240 #endif /* readv */
241 #if HAVE_EXTRA_OSF_SYMBOLS
242 #define readv(d, iov, iovcnt)            sys_Ereadv(d, iov, iovcnt)
243 #else
244 #define readv(d, iov, iovcnt)            sys_readv(d, iov, iovcnt)
245 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
246 
247 #ifdef recv
248 #undef recv
249 #endif /* recv */
250 #define recv(s, msg, len, flags)         sys_recv(s, msg, len, flags)
251 
252 #ifdef recvfrom
253 #undef recvfrom
254 #endif /* recvfrom */
255 #if HAVE_EXTRA_OSF_SYMBOLS
256 #define recvfrom(s, buf, len, flags, from, fromlen)   \
257         sys_Erecvfrom(s, buf, len, flags, from, fromlen)
258 #else
259 #define recvfrom(s, buf, len, flags, from, fromlen)   \
260         sys_recvfrom(s, buf, len, flags, from, fromlen)
261 
262 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
263 
264 #ifdef recvmsg
265 #undef recvmsg
266 #endif /* recvmsg */
267 #if (defined __sun) && (defined _XPG4_2)
268 #define recvmsg(s, msg, flags)          sys_xnet_recvmsg(s, msg, flags)
269 #else
270 #define recvmsg(s, msg, flags)          sys_recvmsg(s, msg, flags)
271 #endif
272 
273 #if HAVE_RRESVPORT
274 #ifdef rresvport
275 #undef rresvport
276 #endif /* rresvport */
277 #define rresvport(port)                  sys_rresvport(port)
278 #endif /* HAVE_RRESVPORT */
279 
280 #ifdef sendto
281 #undef sendto
282 #endif /* sendto */
283 #if (defined __sun) && (defined _XPG4_2)
284 #define sendto(s, msg, len, flags, to, tolen)   \
285         sys_xnet_sendto(s, msg, len, flags, to, tolen)
286 #else
287 #define sendto(s, msg, len, flags, to, tolen)   \
288         sys_sendto(s, msg, len, flags, to, tolen)
289 #endif
290 
291 #ifdef write
292 #undef write
293 #endif /* write */
294 #define write(d, buf, nbytes)            sys_write(d, buf, nbytes)
295 
296 #ifdef writev
297 #undef writev
298 #endif /* writev */
299 #if HAVE_EXTRA_OSF_SYMBOLS
300 #define writev(d, iov, iovcnt)         sys_Ewritev(d, iov, iovcnt)
301 #else
302 #define writev(d, iov, iovcnt)         sys_writev(d, iov, iovcnt)
303 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
304 
305 #ifdef send
306 #undef send
307 #endif /* send */
308 #define send(s, msg, len, flags)         sys_send(s, msg, len, flags)
309 
310 #undef sendmsg
311 #if HAVE_EXTRA_OSF_SYMBOLS
312 #define sendmsg(s, msg, flags)         sys_Esendmsg(s, msg, flags)
313 #else
314 #if (defined __sun) && (defined _XPG4_2)
315 #define sendmsg(s, msg, flags)         sys_xnet_sendmsg(s, msg, flags)
316 #else
317 #define sendmsg(s, msg, flags)         sys_sendmsg(s, msg, flags)
318 #endif
319 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
320 
321 #undef recvmsg
322 #if HAVE_EXTRA_OSF_SYMBOLS
323 #define recvmsg(s, msg, flags)         sys_Erecvmsg(s, msg, flags)
324 #else
325 #if (defined __sun) && (defined _XPG4_2)
326 #define recvmsg(s, msg, flags)         sys_xnet_recvmsg(s, msg, flags)
327 #else
328 #define recvmsg(s, msg, flags)         sys_recvmsg(s, msg, flags)
329 #endif
330 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
331 
332 #if HAVE_GSSAPI && HAVE_LINUX_GLIBC_WORKAROUND
333 #ifdef getc
334 #undef getc
335 #endif /* getc */
336 #define getc(s)                           sys_getc(s)
337 
338 #ifdef fgetc
339 #undef fgetc
340 #endif /* fgetc */
341 #define fgetc(s)                          sys_fgetc(s)
342 
343 #ifdef gets
344 #undef gets
345 #endif /* gets */
346 #define gets(s)                           sys_gets(s)
347 
348 #ifdef fgets
349 #undef fgets
350 #endif /* fgets */
351 #define fgets(c, i, s)                    sys_fgets(c, i, s)
352 
353 #ifdef putc
354 #undef putc
355 #endif /* putc */
356 #define putc(c, s)                        sys_putc(c, s)
357 
358 #ifdef fputc
359 #undef fputc
360 #endif /* fputc */
361 #define fputc(c, s)                       sys_fputc(c, s)
362 
363 #ifdef puts
364 #undef pus
365 #endif /* puts */
366 #define puts(b)                           sys_puts(b)
367 
368 #ifdef fputs
369 #undef fputs
370 #endif /* fputc */
371 #define fputs(b, s)                       sys_fputs(b, s)
372 
373 #ifdef fflush
374 #undef fflush
375 #endif /* fflush */
376 #define fflush(s)                         sys_fflush(s)
377 
378 #ifdef fclose
379 #undef fclose
380 #endif /* fclose */
381 #define fclose(s)                         sys_fclose(s)
382 
383 #ifdef printf
384 #undef printf
385 #endif /* printf */
386 #define printf(f, ...)                    sys_printf(f, __VA_ARGS__ )
387 
388 #ifdef vprintf
389 #undef vprintf
390 #endif /* vprintf */
391 #define vprintf(f, v)                     sys_vfprintf(f, v)
392 
393 #ifdef fprintf
394 #undef fprintf
395 #endif /* fprintf */
396 #define fprintf(s, ...)                   sys_fprintf(s, __VA_ARGS__ )
397 
398 #ifdef vfprintf
399 #undef vfprintf
400 #endif /* vfprintf */
401 #define vfprintf(s, f, v)                 sys_vfprintf(s, f, v)
402 
403 #ifdef fwrite
404 #undef fwrite
405 #endif /* fwrite */
406 #define fwrite(p, i, n, s)                sys_fwrite(p, i, n, s)
407 
408 #ifdef fread
409 #undef fread
410 #endif /* fread */
411 #define fread(p, i, n, s)                 sys_fread(p, i, n, s)
412 
413 #endif /* HAVE_GSSAPI && HAVE_LINUX_GLIBC_WORKAROUND */
414 
415 #endif /* SOCKSLIBRARY_DYNAMIC */
416 
417 /* not used in client. */
418 #define loglevel_errno(e,  side) (LOG_DEBUG)
419 #define loglevel_gaierr(e, side) (LOG_DEBUG)
420 
421 #define FDPASS_MAX         2   /* max number of descriptors we send/receive.  */
422 
423 typedef struct {
424    unsigned char      inited;
425 
426    unsigned char      havegssapisockets;/* have any gssapi-sockets?           */
427    unsigned char      threadlockenabled;/* is threadlocking enabled?          */
428 
429    ssize_t            executingdnscode; /* exec. gethost*()/getname*()/etc.   */
430    unsigned char      internalerrordetected;
431    sig_atomic_t       insignal;         /* executing in signalhandler?        */
432    sig_atomic_t       handledsignal;   /*
433                                         * between now and the time this
434                                         * variable was last cleared, did we
435                                         * handle a signal?
436                                         */
437 
438    sockshost_t        lastconnect;      /* address we last connected to.      */
439    pid_t              pid;              /* our pid.                           */
440    rlim_t             maxopenfiles;
441 } configstate_t;
442 
443 typedef struct {
444    int               debug;
445    int               directfallback; /* fallback to direct connections        */
446    char              *configfile;    /* name of current configfile.           */
447 } option_t;
448 
449 struct config {
450    pid_t                    connectchild;            /* connect process.      */
451    int                      child_data;              /* data socket to child. */
452    int                      child_ack;               /* ack to child.         */
453 
454    char                     domain[MAXHOSTNAMELEN];  /* localdomain.          */
455 
456    logtype_t                errlog;                  /* for errors only.      */
457    logtype_t                log;                     /* where to log.         */
458    int                      loglock;                 /* lockfile for logging. */
459 
460    option_t                 option;                  /* misc. options.        */
461    int                      resolveprotocol;         /* resolveprotocol.      */
462 
463    routeoptions_t           routeoptions;            /* global route flags.   */
464    route_t                  *route;                  /* linked list of routes */
465 
466    /* XXX not supported in client yet. */
467    socketoption_t           *socketoptionv;          /* global socket options.*/
468    size_t                   socketoptionc;
469 
470    configstate_t            state;
471    timeout_t                timeout;
472 };
473 
474 typedef struct {
475    int           s;         /* socket used for control-connection.     */
476    socks_t       packet;    /* socks packet exchanged with server.     */
477 } childpacket_t;
478 
479 typedef sigset_t addrlockopaque_t;
480 
481 /*
482  * libsocks function declarations
483  */
484 
485 void __ATTRIBUTE__((ATTRIBUTE_CONSTRUCTOR))
486 clientinit(void);
487 /*
488  * initializes client state, reads config file, etc.
489  */
490 
491 #if !HAVE_OSF_OLDSTYLE
492 int Raccept(int, struct sockaddr *, socklen_t *);
493 int Rconnect(int, const struct sockaddr *, socklen_t);
494 int Rgetsockname(int, struct sockaddr *, socklen_t *);
495 int Rgetsockopt(int, int, int, void *, socklen_t *);
496 int Rgetpeername(int, struct sockaddr *, socklen_t *);
497 ssize_t Rsendto(int s, const void *msg, size_t len, int flags,
498                 const struct sockaddr *to, socklen_t tolen)
499       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
500 ssize_t Rrecvfrom(int s, void *buf, size_t len, int flags,
501                   struct sockaddr * from, socklen_t *fromlen)
502       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
503 ssize_t Rsendmsg(int s, const struct msghdr *msg, int flags);
504 ssize_t Rrecvmsg(int s, struct msghdr *msg, int flags);
505 int Rbind(int, const struct sockaddr *, socklen_t);
506 #endif /* !HAVE_OSF_OLDSTYLE */
507 
508 int Rbindresvport(int, struct sockaddr_in *);
509 int Rrresvport(int *);
510 struct hostent *Rgethostbyname(const char *);
511 struct hostent *Rgethostbyname2(const char *, int af);
512 
513 #if HAVE_GETNAMEINFO
514 
515 int Rgetnameinfo(const struct sockaddr *sa, socklen_t salen, char *host,
516                  socklen_t hostlen, char *serv, socklen_t servlen,
517                  int flags);
518 
519 #endif /* HAVE_GETNAMEINFO  */
520 
521 #if HAVE_GETADDRINFO
522 int Rgetaddrinfo(const char *nodename, const char *servname,
523                  const struct addrinfo *hints, struct addrinfo **res);
524 #endif /* HAVE_GETADDRINFO */
525 
526 #if HAVE_GETIPNODEBYNAME
527 struct hostent *Rgetipnodebyname(const char *, int, int, int *);
528 void Rfreehostent(struct hostent *);
529 #endif /* HAVE_GETIPNODEBYNAME */
530 
531 ssize_t Rwrite(int d, const void *buf, size_t nbytes)
532       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
533 ssize_t Rwritev(int d, const struct iovec *iov, int iovcnt);
534 ssize_t Rsend(int s, const void *msg, size_t len, int flags)
535       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
536 ssize_t Rread(int d, void *buf, size_t nbytes)
537       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
538 ssize_t Rreadv(int d, const struct iovec *iov, int iovcnt);
539 ssize_t Rrecv(int s, void *msg, size_t len, int flags)
540       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
541 
542 #if HAVE_GSSAPI && HAVE_LINUX_GLIBC_WORKAROUND
543 int Rfgetc(FILE *fp);
544 char *Rgets(char *s);
545 char *Rfgets(char *s, int size, FILE *fp);
546 int Rfputc(int c, FILE *fp);
547 int Rfputs(const char *s, FILE *fp);
548 int Rfflush(FILE *fp);
549 int Rfclose(FILE *fp);
550 int Rfprintf(FILE *stream, const char *format, ...);
551 int Rvfprintf(FILE *stream, const char *format, va_list ap);
552 size_t Rfread(void *ptr, size_t size, size_t nmemb, FILE *s);
553 size_t Rfwrite(const void *ptr, size_t size, size_t nmemb, FILE *s);
554 #endif /* HAVE_GSSAPI && HAVE_LINUX_GLIBC_WORKAROUND */
555 
556 
557 int SOCKSinit(char *);
558 int Rlisten(int, int);
559 int Rselect(int, fd_set *, fd_set *, fd_set *, struct timeval *);
560 /*
561  * unused functions needed to compile programs with support for other
562  * socks implementations.
563  */
564 
565 
566 
567 
568 int
569 cgetaddrinfo(const char *name, const char *service,
570              const struct addrinfo *hints, struct addrinfo **res,
571              dnsinfo_t *resmem);
572 /*
573  * Like getaddrinfo(3), but "resmem" is used to hold the contents of "res",
574  * rather than allocating the memory for "res" dynamically and then
575  * having to call freeaddrinfo(3).
576  */
577 
578 route_t *
579 udpsetup(int s, const struct sockaddr_storage *to, int type, int shouldconnect,
580          char *emsg, const size_t emsglen);
581 /*
582  * sets up udp relaying between address of "s" and "to" by connecting
583  * to a proxy server.
584  * If relaying is already set up the function returns with success.
585  * "type" is the type of connection to set up, SOCKS_SEND or SOCKS_RECV.
586  * "shouldconnect" indicates whether the socket should be connected or not.
587  *
588  * Returns the route that was used (possibly a direct route), or NULL if no
589  * route could be set up.  In the latter case, errno and emsg will be set.
590  */
591 
592 int
593 fd_is_network_socket(const int fd);
594 /*
595  * Returns true if "fd" is a network socket of a kind we support.
596  * Returns False otherwise.
597  */
598 
599 
600 
601 
602    /*
603     *  Misc. functions to help keep track of our connection(s) to the server.
604     */
605 
606 void socks_addrinit(void);
607 /*
608  * inits thing, including memory and locks, for socks_addaddr()-functions.
609  */
610 
611 void socks_addrlock(const int locktype, addrlockopaque_t *opaque);
612 void socks_addrunlock(const addrlockopaque_t *opaque);
613 /*
614  * Lock/unlock global address object.
615  * "type" is one of F_WRLCK or F_RDLCK, for write or read-lock.
616  * "opaque" is a pointer filled in by "socks_addrlock()", and
617  * the same pointer needs to be passed to socks_addrunlock();
618  */
619 
620 socksfd_t *
621 socks_addrdup(const socksfd_t *old, socksfd_t *new);
622 /*
623  * Duplicates "old", in "new".
624  * Returns:
625  *    On success: "new".
626  *    On failure: NULL (resource shortage).
627  */
628 
629 socksfd_t *
630 socks_addaddr(const int clientfd, const socksfd_t *socksaddress,
631               const int takelock);
632 /*
633  * "clientfd" is associated with the structure "socksfd".
634  * If "takelock" is true, it means the function should take the
635  * socksfdv/addrlock.
636  *
637  * The function duplicates all arguments in it's own form and does
638  * not access the memory referenced by them afterwards.
639  *
640  * The function checks the state of all file descriptors on each call and
641  * removes those that are no longer open.
642  *
643  * Returns:
644  *      On success: pointer to the added socksfd_t structure.
645  *      On failure: exits.  (memory exhausted and process grew descriptor size.)
646  *
647  */
648 
649 socksfd_t *
650 socks_getaddr(const int fd, socksfd_t *socksfd, const int takelock);
651 /*
652  * Returns a copy of the socksfd corresponding to "fd".
653  * If "socksfd" is not NULL, the contents of the socksfd is also stored in
654  * "socksfd".
655  *
656  * If "takelock" is true, it means the function should take the
657  * socksfdv/addrlock.
658  *
659  * Returns:
660  *      On success:  the socket address associated with file descriptor "fd".
661  *      On failure:    NULL.  (no socket address associated with "fd").
662  */
663 
664 void
665 socks_rmaddr(const int s, const int takelock);
666 /*
667  * If "takelock" is true, it means the function should take the
668  * socksfdv/addrlock.
669  *
670  * removes the association for the socket "s", also closes the server
671  * connection.  If "s" is not registered the request is ignored.
672  */
673 
674 int
675 socks_addrcontrol(const int controlsent, const int controlreceived,
676                   const int takelock);
677 /*
678  * Goes through all addresses registered and tries to find one where
679  * the control socket has a local address of "local" and peer address
680  * of "remote".
681  *
682  * "controlsent" gives the expected fd index for control, if not -1.
683  * That is the fd index control had when we sent the request to
684  * our connect-child, and may belong to another fd now.
685  *
686  * "controlreceived" is the actual fd we sent to the connectchild, and
687  * which we now receive back from it.
688  *
689  *   Returns:
690  *      On success: the descriptor the socksfd struct was registered with.
691  *      On failure: -1
692  */
693 
694 int
695 socks_addrmatch(const struct sockaddr_storage *local,
696                 const struct sockaddr_storage *remote,
697                 const socksstate_t *state, const int takelock);
698 /*
699  * If "takelock" is true, it means the function should take the
700  * socksfdv/addrlock.
701  *
702  * Goes through all addresses registered and tries to find one where
703  * all arguments match.
704  * Arguments that are NULL or have "illegal" values are ignored.
705  * Returns:
706  *      On success: the descriptor the socksfd with matching arguments was
707  *                registered with (>= 0).
708  *      On failure: -1.
709  */
710 
711 int
712 socks_addrisours(const int s, socksfd_t *socksfd, const int takelock);
713 /*
714  * Compares the current address of "s" to the registered address.
715  * If there is a mismatch, the function will try to correct it if possible.
716  *
717  * If "takelock" is true, it means the function should take the
718  * socksfdv/addrlock.
719  *
720  * If the current address matches the registered address and "socksfd"
721  * is not NULL, "socksfd" is filled in with the data of the matching socket.
722  *
723  * Returns:
724  *      If current address found to match registered: true.
725  *      Else: false.
726  */
727 
728 void
729 update_after_negotiate(const socks_t *packet, socksfd_t *socksfd);
730 /*
731  * Updates "socksfd" after a successful socks_negotiate() using
732  * that used "packet".
733  */
734 
735 int
736 fdisopen(int fd);
737 /*
738  * returns 1 if the file descriptor "fd" currently references a open object.
739  * returns 0 otherwise.
740  */
741 
742 
743 #if DIAGNOSTIC
744 void
745 cc_socksfdv(int sig);
746 /*
747  * consistency check on socksfdv.
748  */
749 #endif /* DIAGNOSTIC */
750 
751 
752 #if SOCKSLIBRARY_DYNAMIC
753 
754 int sys_rresvport(int *);
755 int sys_bindresvport(int, struct sockaddr_in *);
756 void sys_freehostent(struct hostent *);
757 
758 HAVE_PROT_READ_0
759 sys_read(HAVE_PROT_READ_1, HAVE_PROT_READ_2, HAVE_PROT_READ_3);
760 HAVE_PROT_LISTEN_0
761 sys_listen(HAVE_PROT_LISTEN_1, HAVE_PROT_LISTEN_2);
762 HAVE_PROT_READV_0
763 sys_readv(HAVE_PROT_READV_1, HAVE_PROT_READV_2, HAVE_PROT_READV_3);
764 HAVE_PROT_RECV_0
765 sys_recv(HAVE_PROT_RECV_1, HAVE_PROT_RECV_2, HAVE_PROT_RECV_3,
766       HAVE_PROT_RECV_4);
767 HAVE_PROT_RECVMSG_0
768 sys_recvmsg(HAVE_PROT_RECVMSG_1, HAVE_PROT_RECVMSG_2, HAVE_PROT_RECVMSG_3);
769 HAVE_PROT_SEND_0
770 sys_send(HAVE_PROT_SEND_1, HAVE_PROT_SEND_2, HAVE_PROT_SEND_3,
771       HAVE_PROT_SEND_4);
772 HAVE_PROT_WRITE_0
773 sys_write(HAVE_PROT_WRITE_1, HAVE_PROT_WRITE_2, HAVE_PROT_WRITE_3);
774 
775 #if HAVE_OSF_OLDSTYLE
776 int sys_accept(int, struct sockaddr *, int *);
777 #else
778 HAVE_PROT_ACCEPT_0
779 sys_accept(HAVE_PROT_ACCEPT_1, HAVE_PROT_ACCEPT_2, HAVE_PROT_ACCEPT_3);
780 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
781 
782 #if HAVE_OSF_OLDSTYLE
783 int sys_bind(int, const struct sockaddr *, int);
784 #else
785 HAVE_PROT_BIND_0
786 sys_bind(HAVE_PROT_BIND_1, HAVE_PROT_BIND_2, HAVE_PROT_BIND_3);
787 #endif /* !HAVE_OSF_OLDSTYLE */
788 
789 #if HAVE_OSF_OLDSTYLE
790 int sys_connect(int, const struct sockaddr *, int);
791 #else
792 HAVE_PROT_CONNECT_0
793 sys_connect(HAVE_PROT_CONNECT_1, HAVE_PROT_CONNECT_2, HAVE_PROT_CONNECT_3);
794 #endif /* HAVE_OSF_OLDSTYLE */
795 
796 #if HAVE_OSF_OLDSTYLE
797 int sys_getpeername(int, struct sockaddr *, int *);
798 #else
799 HAVE_PROT_GETPEERNAME_0
800 sys_getpeername(HAVE_PROT_GETPEERNAME_1, HAVE_PROT_GETPEERNAME_2,
801       HAVE_PROT_GETPEERNAME_3);
802 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
803 
804 #if HAVE_OSF_OLDSTYLE
805 int sys_getsockname(int, struct sockaddr *, int *);
806 #else
807 HAVE_PROT_GETSOCKNAME_0
808 sys_getsockname(HAVE_PROT_GETSOCKNAME_1, HAVE_PROT_GETSOCKNAME_2,
809       HAVE_PROT_GETSOCKNAME_3);
810 HAVE_PROT_GETSOCKNAME_0
811 sys_getsockname_notracking(HAVE_PROT_GETSOCKNAME_1, HAVE_PROT_GETSOCKNAME_2,
812       HAVE_PROT_GETSOCKNAME_3);
813 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
814 
815 HAVE_PROT_GETSOCKOPT_0
816 sys_getsockopt(HAVE_PROT_GETSOCKOPT_1, HAVE_PROT_GETSOCKOPT_2,
817       HAVE_PROT_GETSOCKOPT_3, HAVE_PROT_GETSOCKOPT_4, HAVE_PROT_GETSOCKOPT_5);
818 
819 #if HAVE_OSF_OLDSTYLE
820 int sys_recvfrom(int, void*, int, int, struct sockaddr *, int *);
821 #else
822 HAVE_PROT_RECVFROM_0
823 sys_recvfrom(HAVE_PROT_RECVFROM_1, HAVE_PROT_RECVFROM_2, HAVE_PROT_RECVFROM_3,
824       HAVE_PROT_RECVFROM_4, HAVE_PROT_RECVFROM_5, HAVE_PROT_RECVFROM_6);
825 #endif /* HAVE_OSF_OLDSTYLE */
826 
827 #if HAVE_OSF_OLDSTYLE
828 ssize_t sys_writev(int, const struct iovec *, int);
829 #else
830 HAVE_PROT_WRITEV_0
831 sys_writev(HAVE_PROT_WRITEV_1, HAVE_PROT_WRITEV_2, HAVE_PROT_WRITEV_3);
832 #endif /* HAVE_OSF_OLDSTYLE */
833 
834 #if HAVE_OSF_OLDSTYLE
835 ssize_t sys_sendmsg(int, struct msghdr *, int);
836 #else
837 HAVE_PROT_SENDMSG_0
838 sys_sendmsg(HAVE_PROT_SENDMSG_1, HAVE_PROT_SENDMSG_2, HAVE_PROT_SENDMSG_3);
839 #endif /* HAVE_OSF_OLDSTYLE */
840 
841 #if HAVE_OSF_OLDSTYLE
842 int sys_sendto(int, const void *, int, int, const struct sockaddr *,
843       socklen_t);
844 #else
845 HAVE_PROT_SENDTO_0
846 sys_sendto(HAVE_PROT_SENDTO_1, HAVE_PROT_SENDTO_2, HAVE_PROT_SENDTO_3,
847       HAVE_PROT_SENDTO_4, HAVE_PROT_SENDTO_5, HAVE_PROT_SENDTO_6);
848 #endif /* HAVE_OSF_OLDSTYLE */
849 
850 #if HAVE_EXTRA_OSF_SYMBOLS
851 int sys_Eaccept(int, struct sockaddr *, socklen_t *);
852 int sys_Egetpeername(int, struct sockaddr *, socklen_t *);
853 int sys_Egetsockname(int, struct sockaddr *, socklen_t *);
854 ssize_t sys_Ereadv(int, const struct iovec *, int);
855 int sys_Erecvfrom(int, void *, size_t, int, struct sockaddr *, size_t *)
856       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
857 ssize_t sys_Erecvmsg(int, struct msghdr *, int);
858 ssize_t sys_Esendmsg(int, const struct msghdr *, int);
859 ssize_t sys_Ewritev(int, const struct iovec *, int);
860 
861 int sys_naccept(int, struct sockaddr *, socklen_t *);
862 int sys_ngetpeername(int, struct sockaddr *, socklen_t *);
863 int sys_ngetsockname(int, struct sockaddr *, socklen_t *);
864 int sys_nrecvfrom(int, void *, size_t, int, struct sockaddr *, size_t *)
865       __ATTRIBUTE__((__BOUNDED__(__buffer__, 2, 3)));
866 ssize_t sys_nrecvmsg(int, struct msghdr *, int);
867 ssize_t sys_nsendmsg(int, const struct msghdr *, int);
868 #endif /* HAVE_EXTRA_OSF_SYMBOLS */
869 
870 #ifdef __sun
871 HAVE_PROT_BIND_0
872 sys_xnet_bind(HAVE_PROT_BIND_1, HAVE_PROT_BIND_2, HAVE_PROT_BIND_3);
873 HAVE_PROT_LISTEN_0
874 sys_xnet_listen(HAVE_PROT_LISTEN_1, HAVE_PROT_LISTEN_2);
875 HAVE_PROT_RECVMSG_0
876 sys_xnet_recvmsg(HAVE_PROT_RECVMSG_1, HAVE_PROT_RECVMSG_2, HAVE_PROT_RECVMSG_3);
877 HAVE_PROT_SENDMSG_0
878 sys_xnet_sendmsg(HAVE_PROT_SENDMSG_1, HAVE_PROT_SENDMSG_2, HAVE_PROT_SENDMSG_3);
879 HAVE_PROT_SENDTO_0
880 sys_xnet_sendto(HAVE_PROT_SENDTO_1, HAVE_PROT_SENDTO_2, HAVE_PROT_SENDTO_3,
881    HAVE_PROT_SENDTO_4, HAVE_PROT_SENDTO_5, HAVE_PROT_SENDTO_6);
882 HAVE_PROT_CONNECT_0
883 sys_xnet_connect(HAVE_PROT_CONNECT_1, HAVE_PROT_CONNECT_2, HAVE_PROT_CONNECT_3);
884 #endif /* __sun */
885 
886 #ifdef __FreeBSD__
887 HAVE_PROT_ACCEPT_0
888 _accept(HAVE_PROT_ACCEPT_1, HAVE_PROT_ACCEPT_2, HAVE_PROT_ACCEPT_3);
889 HAVE_PROT_BIND_0
890 _bind(HAVE_PROT_BIND_1, HAVE_PROT_BIND_2, HAVE_PROT_BIND_3);
891 HAVE_PROT_CONNECT_0
892 _connect(HAVE_PROT_CONNECT_1, HAVE_PROT_CONNECT_2, HAVE_PROT_CONNECT_3);
893 HAVE_PROT_GETPEERNAME_0
894 _getpeername(HAVE_PROT_GETPEERNAME_1, HAVE_PROT_GETPEERNAME_2,
895     HAVE_PROT_GETPEERNAME_3);
896 HAVE_PROT_GETSOCKNAME_0
897 _getsockname(HAVE_PROT_GETSOCKNAME_1, HAVE_PROT_GETSOCKNAME_2,
898     HAVE_PROT_GETSOCKNAME_3);
899 HAVE_PROT_GETSOCKOPT_0
900 _getsockopt(HAVE_PROT_GETSOCKOPT_1, HAVE_PROT_GETSOCKOPT_2,
901     HAVE_PROT_GETSOCKOPT_3, HAVE_PROT_GETSOCKOPT_4, HAVE_PROT_GETSOCKOPT_5);
902 HAVE_PROT_LISTEN_0
903 _listen(HAVE_PROT_LISTEN_1, HAVE_PROT_LISTEN_2);
904 HAVE_PROT_READ_0
905 _read(HAVE_PROT_READ_1, HAVE_PROT_READ_2, HAVE_PROT_READ_3);
906 HAVE_PROT_READV_0
907 _readv(HAVE_PROT_READV_1, HAVE_PROT_READV_2, HAVE_PROT_READV_3);
908 HAVE_PROT_RECV_0
909 _recv(HAVE_PROT_RECV_1, HAVE_PROT_RECV_2, HAVE_PROT_RECV_3, HAVE_PROT_RECV_4);
910 HAVE_PROT_RECVFROM_0
911 _recvfrom(HAVE_PROT_RECVFROM_1, HAVE_PROT_RECVFROM_2, HAVE_PROT_RECVFROM_3,
912     HAVE_PROT_RECVFROM_4, HAVE_PROT_RECVFROM_5, HAVE_PROT_RECVFROM_6);
913 HAVE_PROT_RECVMSG_0
914 _recvmsg(HAVE_PROT_RECVMSG_1, HAVE_PROT_RECVMSG_2, HAVE_PROT_RECVMSG_3);
915 HAVE_PROT_WRITE_0
916 _write(HAVE_PROT_WRITE_1, HAVE_PROT_WRITE_2, HAVE_PROT_WRITE_3);
917 HAVE_PROT_WRITEV_0
918 _writev(HAVE_PROT_WRITEV_1, HAVE_PROT_WRITEV_2, HAVE_PROT_WRITEV_3);
919 HAVE_PROT_SEND_0
920 _send(HAVE_PROT_SEND_1, HAVE_PROT_SEND_2, HAVE_PROT_SEND_3, HAVE_PROT_SEND_4);
921 HAVE_PROT_SENDMSG_0
922 _sendmsg(HAVE_PROT_SENDMSG_1, HAVE_PROT_SENDMSG_2, HAVE_PROT_SENDMSG_3);
923 HAVE_PROT_SENDTO_0
924 _sendto(HAVE_PROT_SENDTO_1, HAVE_PROT_SENDTO_2, HAVE_PROT_SENDTO_3,
925     HAVE_PROT_SENDTO_4, HAVE_PROT_SENDTO_5, HAVE_PROT_SENDTO_6);
926 #endif /* __FreeBSD__ */
927 
928 #if HAVE_GSSAPI && HAVE_LINUX_GLIBC_WORKAROUND
929 HAVE_PROT_GETC_0
930 sys_getc(HAVE_PROT_GETC_1);
931 HAVE_PROT_FGETC_0
932 sys_fgetc(HAVE_PROT_FGETC_1);
933 HAVE_PROT_GETS_0
934 sys_gets(HAVE_PROT_GETS_1);
935 HAVE_PROT_FGETS_0
936 sys_fgets(HAVE_PROT_FGETS_1, HAVE_PROT_FGETS_2, HAVE_PROT_FGETS_3);
937 HAVE_PROT_PUTC_0
938 sys_putc(HAVE_PROT_PUTC_1, HAVE_PROT_PUTC_2);
939 HAVE_PROT_FPUTC_0
940 sys_fputc(HAVE_PROT_FPUTC_1, HAVE_PROT_FPUTC_2);
941 HAVE_PROT_PUTS_0
942 sys_puts(HAVE_PROT_PUTS_1);
943 HAVE_PROT_FPUTS_0
944 sys_fputs(HAVE_PROT_FPUTS_1, HAVE_PROT_FPUTS_2);
945 HAVE_PROT_FFLUSH_0
946 sys_fflush(HAVE_PROT_FFLUSH_1);
947 HAVE_PROT_FCLOSE_0
948 sys_fclose(HAVE_PROT_FCLOSE_1);
949 HAVE_PROT_PRINTF_0
950 sys_printf(HAVE_PROT_PRINTF_1, ...);
951 HAVE_PROT_VPRINTF_0
952 sys_vprintf(HAVE_PROT_VPRINTF_1, HAVE_PROT_VPRINTF_2);
953 HAVE_PROT_FPRINTF_0
954 sys_fprintf(HAVE_PROT_FPRINTF_1, HAVE_PROT_FPRINTF_2, ...);
955 HAVE_PROT_VFPRINTF_0
956 sys_vfprintf(HAVE_PROT_VFPRINTF_1, HAVE_PROT_VFPRINTF_2, HAVE_PROT_VFPRINTF_3);
957 HAVE_PROT_FWRITE_0
958 sys_fwrite(HAVE_PROT_FWRITE_1, HAVE_PROT_FWRITE_2, HAVE_PROT_FWRITE_3,
959       HAVE_PROT_FWRITE_4);
960 HAVE_PROT_FREAD_0
961 sys_fread(HAVE_PROT_FREAD_1, HAVE_PROT_FREAD_2, HAVE_PROT_FREAD_3,
962       HAVE_PROT_FREAD_4);
963 #endif /* HAVE_GSSAPI && HAVE_LINUX_GLIBC_WORKAROUND */
964 
965 #if HAVE_DARWIN
966 
967 HAVE_PROT_READ_0
968 sys_read_nocancel(HAVE_PROT_READ_1, HAVE_PROT_READ_2, HAVE_PROT_READ_3);
969 HAVE_PROT_CONNECT_0
970 sys_connect_nocancel(HAVE_PROT_CONNECT_1, HAVE_PROT_CONNECT_2,
971    HAVE_PROT_CONNECT_3 namelen);
972 HAVE_PROT_RECVFROM_0
973 sys_recvfrom_nocancel(HAVE_PROT_RECVFROM_1, HAVE_PROT_RECVFROM_2,
974    HAVE_PROT_RECVFROM_3, HAVE_PROT_RECVFROM_4, HAVE_PROT_RECVFROM_5,
975    HAVE_PROT_RECVFROM_6);
976 HAVE_PROT_SENDTO_0
977 sys_sendto_nocancel(HAVE_PROT_SENDTO_1, HAVE_PROT_SENDTO_2, HAVE_PROT_SENDTO_3,
978    HAVE_PROT_SENDTO_4, HAVE_PROT_SENDTO_5, HAVE_PROT_SENDTO_6);
979 HAVE_PROT_WRITE_0
980 sys_write_nocancel(HAVE_PROT_WRITE_1, HAVE_PROT_WRITE_2, HAVE_PROT_WRITE_3);
981 
982 #endif /* HAVE_DARWIN */
983 
984 #endif /* SOCKSLIBRARY_DYNAMIC */
985 
986 #endif /* !_SOCKS_H_ */
987