xref: /minix3/sys/sys/socketvar.h (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1*0a6a1f1dSLionel Sambuc /*	$NetBSD: socketvar.h,v 1.139 2015/05/09 15:22:47 rtr Exp $	*/
26c8f7fc3SBen Gras 
36c8f7fc3SBen Gras /*-
46c8f7fc3SBen Gras  * Copyright (c) 2008, 2009 The NetBSD Foundation, Inc.
56c8f7fc3SBen Gras  * All rights reserved.
66c8f7fc3SBen Gras  *
76c8f7fc3SBen Gras  * This code is derived from software contributed to The NetBSD Foundation
86c8f7fc3SBen Gras  * by Andrew Doran.
96c8f7fc3SBen Gras  *
106c8f7fc3SBen Gras  * Redistribution and use in source and binary forms, with or without
116c8f7fc3SBen Gras  * modification, are permitted provided that the following conditions
126c8f7fc3SBen Gras  * are met:
136c8f7fc3SBen Gras  * 1. Redistributions of source code must retain the above copyright
146c8f7fc3SBen Gras  *    notice, this list of conditions and the following disclaimer.
156c8f7fc3SBen Gras  * 2. Redistributions in binary form must reproduce the above copyright
166c8f7fc3SBen Gras  *    notice, this list of conditions and the following disclaimer in the
176c8f7fc3SBen Gras  *    documentation and/or other materials provided with the distribution.
186c8f7fc3SBen Gras  *
196c8f7fc3SBen Gras  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
206c8f7fc3SBen Gras  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
216c8f7fc3SBen Gras  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
226c8f7fc3SBen Gras  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
236c8f7fc3SBen Gras  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
246c8f7fc3SBen Gras  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
256c8f7fc3SBen Gras  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
266c8f7fc3SBen Gras  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
276c8f7fc3SBen Gras  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
286c8f7fc3SBen Gras  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
296c8f7fc3SBen Gras  * POSSIBILITY OF SUCH DAMAGE.
306c8f7fc3SBen Gras  */
316c8f7fc3SBen Gras 
326c8f7fc3SBen Gras /*-
336c8f7fc3SBen Gras  * Copyright (c) 1982, 1986, 1990, 1993
346c8f7fc3SBen Gras  *	The Regents of the University of California.  All rights reserved.
356c8f7fc3SBen Gras  *
366c8f7fc3SBen Gras  * Redistribution and use in source and binary forms, with or without
376c8f7fc3SBen Gras  * modification, are permitted provided that the following conditions
386c8f7fc3SBen Gras  * are met:
396c8f7fc3SBen Gras  * 1. Redistributions of source code must retain the above copyright
406c8f7fc3SBen Gras  *    notice, this list of conditions and the following disclaimer.
416c8f7fc3SBen Gras  * 2. Redistributions in binary form must reproduce the above copyright
426c8f7fc3SBen Gras  *    notice, this list of conditions and the following disclaimer in the
436c8f7fc3SBen Gras  *    documentation and/or other materials provided with the distribution.
446c8f7fc3SBen Gras  * 3. Neither the name of the University nor the names of its contributors
456c8f7fc3SBen Gras  *    may be used to endorse or promote products derived from this software
466c8f7fc3SBen Gras  *    without specific prior written permission.
476c8f7fc3SBen Gras  *
486c8f7fc3SBen Gras  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
496c8f7fc3SBen Gras  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
506c8f7fc3SBen Gras  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
516c8f7fc3SBen Gras  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
526c8f7fc3SBen Gras  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
536c8f7fc3SBen Gras  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
546c8f7fc3SBen Gras  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
556c8f7fc3SBen Gras  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
566c8f7fc3SBen Gras  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
576c8f7fc3SBen Gras  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
586c8f7fc3SBen Gras  * SUCH DAMAGE.
596c8f7fc3SBen Gras  *
606c8f7fc3SBen Gras  *	@(#)socketvar.h	8.3 (Berkeley) 2/19/95
616c8f7fc3SBen Gras  */
626c8f7fc3SBen Gras 
636c8f7fc3SBen Gras #ifndef _SYS_SOCKETVAR_H_
646c8f7fc3SBen Gras #define	_SYS_SOCKETVAR_H_
656c8f7fc3SBen Gras 
666c8f7fc3SBen Gras #include <sys/select.h>
676c8f7fc3SBen Gras #include <sys/selinfo.h>		/* for struct selinfo */
686c8f7fc3SBen Gras #include <sys/queue.h>
696c8f7fc3SBen Gras #include <sys/mutex.h>
706c8f7fc3SBen Gras #include <sys/condvar.h>
716c8f7fc3SBen Gras 
726c8f7fc3SBen Gras #if !defined(_KERNEL)
736c8f7fc3SBen Gras struct uio;
746c8f7fc3SBen Gras struct lwp;
756c8f7fc3SBen Gras struct uidinfo;
766c8f7fc3SBen Gras #else
776c8f7fc3SBen Gras #include <sys/uidinfo.h>
786c8f7fc3SBen Gras #endif
796c8f7fc3SBen Gras 
806c8f7fc3SBen Gras TAILQ_HEAD(soqhead, socket);
816c8f7fc3SBen Gras 
826c8f7fc3SBen Gras /*
836c8f7fc3SBen Gras  * Variables for socket buffering.
846c8f7fc3SBen Gras  */
856c8f7fc3SBen Gras struct sockbuf {
866c8f7fc3SBen Gras 	struct selinfo sb_sel;		/* process selecting read/write */
876c8f7fc3SBen Gras 	struct mowner *sb_mowner;	/* who owns data for this sockbuf */
886c8f7fc3SBen Gras 	struct socket *sb_so;		/* back pointer to socket */
896c8f7fc3SBen Gras 	kcondvar_t sb_cv;		/* notifier */
906c8f7fc3SBen Gras 	/* When re-zeroing this struct, we zero from sb_startzero to the end */
916c8f7fc3SBen Gras #define	sb_startzero	sb_cc
926c8f7fc3SBen Gras 	u_long	sb_cc;			/* actual chars in buffer */
936c8f7fc3SBen Gras 	u_long	sb_hiwat;		/* max actual char count */
946c8f7fc3SBen Gras 	u_long	sb_mbcnt;		/* chars of mbufs used */
956c8f7fc3SBen Gras 	u_long	sb_mbmax;		/* max chars of mbufs to use */
966c8f7fc3SBen Gras 	long	sb_lowat;		/* low water mark */
976c8f7fc3SBen Gras 	struct mbuf *sb_mb;		/* the mbuf chain */
986c8f7fc3SBen Gras 	struct mbuf *sb_mbtail;		/* the last mbuf in the chain */
996c8f7fc3SBen Gras 	struct mbuf *sb_lastrecord;	/* first mbuf of last record in
1006c8f7fc3SBen Gras 					   socket buffer */
1016c8f7fc3SBen Gras 	int	sb_flags;		/* flags, see below */
1026c8f7fc3SBen Gras 	int	sb_timeo;		/* timeout for read/write */
1036c8f7fc3SBen Gras 	u_long	sb_overflowed;		/* # of drops due to full buffer */
1046c8f7fc3SBen Gras };
1056c8f7fc3SBen Gras 
1066c8f7fc3SBen Gras #ifndef SB_MAX
1076c8f7fc3SBen Gras #define	SB_MAX		(256*1024)	/* default for max chars in sockbuf */
1086c8f7fc3SBen Gras #endif
1096c8f7fc3SBen Gras 
1106c8f7fc3SBen Gras #define	SB_LOCK		0x01		/* lock on data queue */
1116c8f7fc3SBen Gras #define	SB_NOTIFY	0x04		/* someone is waiting for data/space */
1126c8f7fc3SBen Gras #define	SB_ASYNC	0x10		/* ASYNC I/O, need signals */
1136c8f7fc3SBen Gras #define	SB_UPCALL	0x20		/* someone wants an upcall */
1146c8f7fc3SBen Gras #define	SB_NOINTR	0x40		/* operations not interruptible */
1156c8f7fc3SBen Gras #define	SB_KNOTE	0x100		/* kernel note attached */
1166c8f7fc3SBen Gras #define	SB_AUTOSIZE	0x800		/* automatically size socket buffer */
1176c8f7fc3SBen Gras 
1186c8f7fc3SBen Gras /*
1196c8f7fc3SBen Gras  * Kernel structure per socket.
1206c8f7fc3SBen Gras  * Contains send and receive buffer queues,
1216c8f7fc3SBen Gras  * handle on protocol and pointer to protocol
1226c8f7fc3SBen Gras  * private data and error information.
1236c8f7fc3SBen Gras  */
124*0a6a1f1dSLionel Sambuc struct so_accf {
125*0a6a1f1dSLionel Sambuc 	struct accept_filter	*so_accept_filter;
126*0a6a1f1dSLionel Sambuc 	void	*so_accept_filter_arg;	/* saved filter args */
127*0a6a1f1dSLionel Sambuc 	char	*so_accept_filter_str;	/* saved user args */
128*0a6a1f1dSLionel Sambuc };
129*0a6a1f1dSLionel Sambuc 
130*0a6a1f1dSLionel Sambuc struct sockaddr;
131*0a6a1f1dSLionel Sambuc 
1326c8f7fc3SBen Gras struct socket {
1336c8f7fc3SBen Gras 	kmutex_t * volatile so_lock;	/* pointer to lock on structure */
1346c8f7fc3SBen Gras 	kcondvar_t	so_cv;		/* notifier */
1356c8f7fc3SBen Gras 	short		so_type;	/* generic type, see socket.h */
1366c8f7fc3SBen Gras 	short		so_options;	/* from socket call, see socket.h */
1376c8f7fc3SBen Gras 	u_short		so_linger;	/* time to linger while closing */
1386c8f7fc3SBen Gras 	short		so_state;	/* internal state flags SS_*, below */
1396c8f7fc3SBen Gras 	int		so_unused;	/* used to be so_nbio */
1406c8f7fc3SBen Gras 	void		*so_pcb;	/* protocol control block */
1416c8f7fc3SBen Gras 	const struct protosw *so_proto;	/* protocol handle */
1426c8f7fc3SBen Gras /*
1436c8f7fc3SBen Gras  * Variables for connection queueing.
1446c8f7fc3SBen Gras  * Socket where accepts occur is so_head in all subsidiary sockets.
1456c8f7fc3SBen Gras  * If so_head is 0, socket is not related to an accept.
1466c8f7fc3SBen Gras  * For head socket so_q0 queues partially completed connections,
1476c8f7fc3SBen Gras  * while so_q is a queue of connections ready to be accepted.
1486c8f7fc3SBen Gras  * If a connection is aborted and it has so_head set, then
1496c8f7fc3SBen Gras  * it has to be pulled out of either so_q0 or so_q.
1506c8f7fc3SBen Gras  * We allow connections to queue up based on current queue lengths
1516c8f7fc3SBen Gras  * and limit on number of queued connections for this socket.
1526c8f7fc3SBen Gras  */
1536c8f7fc3SBen Gras 	struct socket	*so_head;	/* back pointer to accept socket */
1546c8f7fc3SBen Gras 	struct soqhead	*so_onq;	/* queue (q or q0) that we're on */
1556c8f7fc3SBen Gras 	struct soqhead	so_q0;		/* queue of partial connections */
1566c8f7fc3SBen Gras 	struct soqhead	so_q;		/* queue of incoming connections */
1576c8f7fc3SBen Gras 	TAILQ_ENTRY(socket) so_qe;	/* our queue entry (q or q0) */
1586c8f7fc3SBen Gras 	short		so_q0len;	/* partials on so_q0 */
1596c8f7fc3SBen Gras 	short		so_qlen;	/* number of connections on so_q */
1606c8f7fc3SBen Gras 	short		so_qlimit;	/* max number queued connections */
1616c8f7fc3SBen Gras 	short		so_timeo;	/* connection timeout */
1626c8f7fc3SBen Gras 	u_short		so_error;	/* error affecting connection */
1636c8f7fc3SBen Gras 	u_short		so_aborting;	/* references from soabort() */
1646c8f7fc3SBen Gras 	pid_t		so_pgid;	/* pgid for signals */
1656c8f7fc3SBen Gras 	u_long		so_oobmark;	/* chars to oob mark */
1666c8f7fc3SBen Gras 	struct sockbuf	so_snd;		/* send buffer */
1676c8f7fc3SBen Gras 	struct sockbuf	so_rcv;		/* receive buffer */
1686c8f7fc3SBen Gras 
1696c8f7fc3SBen Gras 	void		*so_internal;	/* Space for svr4 stream data */
1706c8f7fc3SBen Gras 	void		(*so_upcall) (struct socket *, void *, int, int);
1716c8f7fc3SBen Gras 	void *		so_upcallarg;	/* Arg for above */
172*0a6a1f1dSLionel Sambuc 	int		(*so_send) (struct socket *, struct sockaddr *,
1736c8f7fc3SBen Gras 					struct uio *, struct mbuf *,
1746c8f7fc3SBen Gras 					struct mbuf *, int, struct lwp *);
1756c8f7fc3SBen Gras 	int		(*so_receive) (struct socket *,
1766c8f7fc3SBen Gras 					struct mbuf **,
1776c8f7fc3SBen Gras 					struct uio *, struct mbuf **,
1786c8f7fc3SBen Gras 					struct mbuf **, int *);
1796c8f7fc3SBen Gras 	struct mowner	*so_mowner;	/* who owns mbufs for this socket */
1806c8f7fc3SBen Gras 	struct uidinfo	*so_uidinfo;	/* who opened the socket */
1816c8f7fc3SBen Gras 	gid_t		so_egid;	/* creator effective gid */
1826c8f7fc3SBen Gras 	pid_t		so_cpid;	/* creator pid */
183*0a6a1f1dSLionel Sambuc 	struct so_accf	*so_accf;
1846c8f7fc3SBen Gras 	kauth_cred_t	so_cred;	/* socket credentials */
1856c8f7fc3SBen Gras };
1866c8f7fc3SBen Gras 
1876c8f7fc3SBen Gras #define	SB_EMPTY_FIXUP(sb)						\
1886c8f7fc3SBen Gras do {									\
1896c8f7fc3SBen Gras 	KASSERT(solocked((sb)->sb_so));					\
1906c8f7fc3SBen Gras 	if ((sb)->sb_mb == NULL) {					\
1916c8f7fc3SBen Gras 		(sb)->sb_mbtail = NULL;					\
1926c8f7fc3SBen Gras 		(sb)->sb_lastrecord = NULL;				\
1936c8f7fc3SBen Gras 	}								\
1946c8f7fc3SBen Gras } while (/*CONSTCOND*/0)
1956c8f7fc3SBen Gras 
1966c8f7fc3SBen Gras /*
1976c8f7fc3SBen Gras  * Socket state bits.
1986c8f7fc3SBen Gras  */
1996c8f7fc3SBen Gras #define	SS_NOFDREF		0x001	/* no file table ref any more */
2006c8f7fc3SBen Gras #define	SS_ISCONNECTED		0x002	/* socket connected to a peer */
2016c8f7fc3SBen Gras #define	SS_ISCONNECTING		0x004	/* in process of connecting to peer */
2026c8f7fc3SBen Gras #define	SS_ISDISCONNECTING	0x008	/* in process of disconnecting */
2036c8f7fc3SBen Gras #define	SS_CANTSENDMORE		0x010	/* can't send more data to peer */
2046c8f7fc3SBen Gras #define	SS_CANTRCVMORE		0x020	/* can't receive more data from peer */
2056c8f7fc3SBen Gras #define	SS_RCVATMARK		0x040	/* at mark on input */
2066c8f7fc3SBen Gras #define	SS_ISABORTING		0x080	/* aborting fd references - close() */
2076c8f7fc3SBen Gras #define	SS_RESTARTSYS		0x100	/* restart blocked system calls */
2086c8f7fc3SBen Gras #define	SS_ISDISCONNECTED	0x800	/* socket disconnected from peer */
2096c8f7fc3SBen Gras 
2106c8f7fc3SBen Gras #define	SS_ASYNC		0x100	/* async i/o notify */
2116c8f7fc3SBen Gras #define	SS_MORETOCOME		0x400	/*
2126c8f7fc3SBen Gras 					 * hint from sosend to lower layer;
2136c8f7fc3SBen Gras 					 * more data coming
2146c8f7fc3SBen Gras 					 */
2156c8f7fc3SBen Gras #define	SS_ISAPIPE 		0x1000	/* socket is implementing a pipe */
2166c8f7fc3SBen Gras #define	SS_NBIO			0x2000	/* socket is in non blocking I/O */
2176c8f7fc3SBen Gras 
2186c8f7fc3SBen Gras #ifdef _KERNEL
2196c8f7fc3SBen Gras 
2206c8f7fc3SBen Gras struct accept_filter {
2216c8f7fc3SBen Gras 	char	accf_name[16];
2226c8f7fc3SBen Gras 	void	(*accf_callback)
2236c8f7fc3SBen Gras 		(struct socket *, void *, int, int);
2246c8f7fc3SBen Gras 	void *	(*accf_create)
2256c8f7fc3SBen Gras 		(struct socket *, char *);
2266c8f7fc3SBen Gras 	void	(*accf_destroy)
2276c8f7fc3SBen Gras 		(struct socket *);
2286c8f7fc3SBen Gras 	LIST_ENTRY(accept_filter) accf_next;
2296c8f7fc3SBen Gras 	u_int	accf_refcnt;
2306c8f7fc3SBen Gras };
2316c8f7fc3SBen Gras 
2326c8f7fc3SBen Gras struct sockopt {
2336c8f7fc3SBen Gras 	int		sopt_level;		/* option level */
2346c8f7fc3SBen Gras 	int		sopt_name;		/* option name */
2356c8f7fc3SBen Gras 	size_t		sopt_size;		/* data length */
2366c8f7fc3SBen Gras 	void *		sopt_data;		/* data pointer */
2376c8f7fc3SBen Gras 	uint8_t		sopt_buf[sizeof(int)];	/* internal storage */
2386c8f7fc3SBen Gras };
2396c8f7fc3SBen Gras 
2406c8f7fc3SBen Gras extern u_long		sb_max;
2416c8f7fc3SBen Gras extern int		somaxkva;
2426c8f7fc3SBen Gras extern int		sock_loan_thresh;
2436c8f7fc3SBen Gras extern kmutex_t		*softnet_lock;
2446c8f7fc3SBen Gras 
2456c8f7fc3SBen Gras struct mbuf;
2466c8f7fc3SBen Gras struct lwp;
2476c8f7fc3SBen Gras struct msghdr;
2486c8f7fc3SBen Gras struct stat;
2496c8f7fc3SBen Gras struct knote;
2506c8f7fc3SBen Gras 
2516c8f7fc3SBen Gras struct	mbuf *getsombuf(struct socket *, int);
2526c8f7fc3SBen Gras 
2536c8f7fc3SBen Gras /*
2546c8f7fc3SBen Gras  * File operations on sockets.
2556c8f7fc3SBen Gras  */
2566c8f7fc3SBen Gras int	soo_read(file_t *, off_t *, struct uio *, kauth_cred_t, int);
2576c8f7fc3SBen Gras int	soo_write(file_t *, off_t *, struct uio *, kauth_cred_t, int);
2586c8f7fc3SBen Gras int	soo_fcntl(file_t *, u_int cmd, void *);
2596c8f7fc3SBen Gras int	soo_ioctl(file_t *, u_long cmd, void *);
2606c8f7fc3SBen Gras int	soo_poll(file_t *, int);
2616c8f7fc3SBen Gras int	soo_kqfilter(file_t *, struct knote *);
2626c8f7fc3SBen Gras int 	soo_close(file_t *);
2636c8f7fc3SBen Gras int	soo_stat(file_t *, struct stat *);
2646c8f7fc3SBen Gras void	soo_restart(file_t *);
2656c8f7fc3SBen Gras void	sbappend(struct sockbuf *, struct mbuf *);
2666c8f7fc3SBen Gras void	sbappendstream(struct sockbuf *, struct mbuf *);
2676c8f7fc3SBen Gras int	sbappendaddr(struct sockbuf *, const struct sockaddr *, struct mbuf *,
2686c8f7fc3SBen Gras 	    struct mbuf *);
2696c8f7fc3SBen Gras int	sbappendaddrchain(struct sockbuf *, const struct sockaddr *,
2706c8f7fc3SBen Gras 	     struct mbuf *, int);
2716c8f7fc3SBen Gras int	sbappendcontrol(struct sockbuf *, struct mbuf *, struct mbuf *);
2726c8f7fc3SBen Gras void	sbappendrecord(struct sockbuf *, struct mbuf *);
2736c8f7fc3SBen Gras void	sbcheck(struct sockbuf *);
2746c8f7fc3SBen Gras void	sbcompress(struct sockbuf *, struct mbuf *, struct mbuf *);
2756c8f7fc3SBen Gras struct mbuf *
2766c8f7fc3SBen Gras 	sbcreatecontrol(void *, int, int, int);
27784d9c625SLionel Sambuc struct mbuf *
27884d9c625SLionel Sambuc 	sbcreatecontrol1(void **, int, int, int, int);
2796c8f7fc3SBen Gras void	sbdrop(struct sockbuf *, int);
2806c8f7fc3SBen Gras void	sbdroprecord(struct sockbuf *);
2816c8f7fc3SBen Gras void	sbflush(struct sockbuf *);
2826c8f7fc3SBen Gras void	sbinsertoob(struct sockbuf *, struct mbuf *);
2836c8f7fc3SBen Gras void	sbrelease(struct sockbuf *, struct socket *);
2846c8f7fc3SBen Gras int	sbreserve(struct sockbuf *, u_long, struct socket *);
2856c8f7fc3SBen Gras int	sbwait(struct sockbuf *);
2866c8f7fc3SBen Gras int	sb_max_set(u_long);
2876c8f7fc3SBen Gras void	soinit(void);
2886c8f7fc3SBen Gras void	soinit1(void);
2896c8f7fc3SBen Gras void	soinit2(void);
2906c8f7fc3SBen Gras int	soabort(struct socket *);
291*0a6a1f1dSLionel Sambuc int	soaccept(struct socket *, struct sockaddr *);
2926c8f7fc3SBen Gras int	sofamily(const struct socket *);
293*0a6a1f1dSLionel Sambuc int	sobind(struct socket *, struct sockaddr *, struct lwp *);
2946c8f7fc3SBen Gras void	socantrcvmore(struct socket *);
2956c8f7fc3SBen Gras void	socantsendmore(struct socket *);
2966c8f7fc3SBen Gras int	soclose(struct socket *);
297*0a6a1f1dSLionel Sambuc int	soconnect(struct socket *, struct sockaddr *, struct lwp *);
2986c8f7fc3SBen Gras int	soconnect2(struct socket *, struct socket *);
2996c8f7fc3SBen Gras int	socreate(int, struct socket **, int, int, struct lwp *,
3006c8f7fc3SBen Gras 		 struct socket *);
301*0a6a1f1dSLionel Sambuc int	fsocreate(int, struct socket **, int, int, int *);
3026c8f7fc3SBen Gras int	sodisconnect(struct socket *);
3036c8f7fc3SBen Gras void	sofree(struct socket *);
3046c8f7fc3SBen Gras int	sogetopt(struct socket *, struct sockopt *);
3056c8f7fc3SBen Gras void	sohasoutofband(struct socket *);
3066c8f7fc3SBen Gras void	soisconnected(struct socket *);
3076c8f7fc3SBen Gras void	soisconnecting(struct socket *);
3086c8f7fc3SBen Gras void	soisdisconnected(struct socket *);
3096c8f7fc3SBen Gras void	soisdisconnecting(struct socket *);
3106c8f7fc3SBen Gras int	solisten(struct socket *, int, struct lwp *);
3116c8f7fc3SBen Gras struct socket *
31284d9c625SLionel Sambuc 	sonewconn(struct socket *, bool);
3136c8f7fc3SBen Gras void	soqinsque(struct socket *, struct socket *, int);
314*0a6a1f1dSLionel Sambuc bool	soqremque(struct socket *, int);
3156c8f7fc3SBen Gras int	soreceive(struct socket *, struct mbuf **, struct uio *,
3166c8f7fc3SBen Gras 	    struct mbuf **, struct mbuf **, int *);
3176c8f7fc3SBen Gras int	soreserve(struct socket *, u_long, u_long);
3186c8f7fc3SBen Gras void	sorflush(struct socket *);
319*0a6a1f1dSLionel Sambuc int	sosend(struct socket *, struct sockaddr *, struct uio *,
3206c8f7fc3SBen Gras 	    struct mbuf *, struct mbuf *, int, struct lwp *);
3216c8f7fc3SBen Gras int	sosetopt(struct socket *, struct sockopt *);
3226c8f7fc3SBen Gras int	so_setsockopt(struct lwp *, struct socket *, int, int, const void *, size_t);
3236c8f7fc3SBen Gras int	soshutdown(struct socket *, int);
3246c8f7fc3SBen Gras void	sorestart(struct socket *);
3256c8f7fc3SBen Gras void	sowakeup(struct socket *, struct sockbuf *, int);
3266c8f7fc3SBen Gras int	sockargs(struct mbuf **, const void *, size_t, int);
3276c8f7fc3SBen Gras int	sopoll(struct socket *, int);
3286c8f7fc3SBen Gras struct	socket *soget(bool);
3296c8f7fc3SBen Gras void	soput(struct socket *);
3306c8f7fc3SBen Gras bool	solocked(struct socket *);
3316c8f7fc3SBen Gras bool	solocked2(struct socket *, struct socket *);
3326c8f7fc3SBen Gras int	sblock(struct sockbuf *, int);
3336c8f7fc3SBen Gras void	sbunlock(struct sockbuf *);
3346c8f7fc3SBen Gras int	sowait(struct socket *, bool, int);
3356c8f7fc3SBen Gras void	solockretry(struct socket *, kmutex_t *);
3366c8f7fc3SBen Gras void	sosetlock(struct socket *);
3376c8f7fc3SBen Gras void	solockreset(struct socket *, kmutex_t *);
3386c8f7fc3SBen Gras 
3396c8f7fc3SBen Gras void	sockopt_init(struct sockopt *, int, int, size_t);
3406c8f7fc3SBen Gras void	sockopt_destroy(struct sockopt *);
3416c8f7fc3SBen Gras int	sockopt_set(struct sockopt *, const void *, size_t);
3426c8f7fc3SBen Gras int	sockopt_setint(struct sockopt *, int);
3436c8f7fc3SBen Gras int	sockopt_get(const struct sockopt *, void *, size_t);
3446c8f7fc3SBen Gras int	sockopt_getint(const struct sockopt *, int *);
3456c8f7fc3SBen Gras int	sockopt_setmbuf(struct sockopt *, struct mbuf *);
3466c8f7fc3SBen Gras struct mbuf *sockopt_getmbuf(const struct sockopt *);
3476c8f7fc3SBen Gras 
3486c8f7fc3SBen Gras int	copyout_sockname(struct sockaddr *, unsigned int *, int, struct mbuf *);
3496c8f7fc3SBen Gras int	copyout_msg_control(struct lwp *, struct msghdr *, struct mbuf *);
3506c8f7fc3SBen Gras void	free_control_mbuf(struct lwp *, struct mbuf *, struct mbuf *);
3516c8f7fc3SBen Gras 
352*0a6a1f1dSLionel Sambuc int	do_sys_getpeername(int, struct sockaddr *);
353*0a6a1f1dSLionel Sambuc int	do_sys_getsockname(int, struct sockaddr *);
3546c8f7fc3SBen Gras int	do_sys_sendmsg(struct lwp *, int, struct msghdr *, int, register_t *);
3556c8f7fc3SBen Gras int	do_sys_recvmsg(struct lwp *, int, struct msghdr *, struct mbuf **,
3566c8f7fc3SBen Gras 	    struct mbuf **, register_t *);
3576c8f7fc3SBen Gras 
358*0a6a1f1dSLionel Sambuc int	do_sys_bind(struct lwp *, int, struct sockaddr *);
359*0a6a1f1dSLionel Sambuc int	do_sys_connect(struct lwp *, int, struct sockaddr *);
360*0a6a1f1dSLionel Sambuc int	do_sys_accept(struct lwp *, int, struct sockaddr *, register_t *,
3616c8f7fc3SBen Gras 	    const sigset_t *, int, int);
3626c8f7fc3SBen Gras 
3636c8f7fc3SBen Gras /*
3646c8f7fc3SBen Gras  * Inline functions for sockets and socket buffering.
3656c8f7fc3SBen Gras  */
3666c8f7fc3SBen Gras 
3676c8f7fc3SBen Gras #include <sys/protosw.h>
3686c8f7fc3SBen Gras #include <sys/mbuf.h>
3696c8f7fc3SBen Gras 
3706c8f7fc3SBen Gras /*
3716c8f7fc3SBen Gras  * Do we need to notify the other side when I/O is possible?
3726c8f7fc3SBen Gras  */
3736c8f7fc3SBen Gras static inline int
sb_notify(struct sockbuf * sb)3746c8f7fc3SBen Gras sb_notify(struct sockbuf *sb)
3756c8f7fc3SBen Gras {
3766c8f7fc3SBen Gras 
3776c8f7fc3SBen Gras 	KASSERT(solocked(sb->sb_so));
3786c8f7fc3SBen Gras 
3796c8f7fc3SBen Gras 	return sb->sb_flags & (SB_NOTIFY | SB_ASYNC | SB_UPCALL | SB_KNOTE);
3806c8f7fc3SBen Gras }
3816c8f7fc3SBen Gras 
3826c8f7fc3SBen Gras /*
3836c8f7fc3SBen Gras  * How much space is there in a socket buffer (so->so_snd or so->so_rcv)?
3846c8f7fc3SBen Gras  * This is problematical if the fields are unsigned, as the space might
3856c8f7fc3SBen Gras  * still be negative (cc > hiwat or mbcnt > mbmax).  Should detect
3866c8f7fc3SBen Gras  * overflow and return 0.
3876c8f7fc3SBen Gras  */
3886c8f7fc3SBen Gras static inline long
sbspace(struct sockbuf * sb)3896c8f7fc3SBen Gras sbspace(struct sockbuf *sb)
3906c8f7fc3SBen Gras {
3916c8f7fc3SBen Gras 
3926c8f7fc3SBen Gras 	KASSERT(solocked(sb->sb_so));
3936c8f7fc3SBen Gras 
3946c8f7fc3SBen Gras 	return lmin(sb->sb_hiwat - sb->sb_cc, sb->sb_mbmax - sb->sb_mbcnt);
3956c8f7fc3SBen Gras }
3966c8f7fc3SBen Gras 
3976c8f7fc3SBen Gras /* do we have to send all at once on a socket? */
3986c8f7fc3SBen Gras static inline int
sosendallatonce(struct socket * so)3996c8f7fc3SBen Gras sosendallatonce(struct socket *so)
4006c8f7fc3SBen Gras {
4016c8f7fc3SBen Gras 
4026c8f7fc3SBen Gras 	return so->so_proto->pr_flags & PR_ATOMIC;
4036c8f7fc3SBen Gras }
4046c8f7fc3SBen Gras 
4056c8f7fc3SBen Gras /* can we read something from so? */
4066c8f7fc3SBen Gras static inline int
soreadable(struct socket * so)4076c8f7fc3SBen Gras soreadable(struct socket *so)
4086c8f7fc3SBen Gras {
4096c8f7fc3SBen Gras 
4106c8f7fc3SBen Gras 	KASSERT(solocked(so));
4116c8f7fc3SBen Gras 
4126c8f7fc3SBen Gras 	return so->so_rcv.sb_cc >= so->so_rcv.sb_lowat ||
4136c8f7fc3SBen Gras 	    (so->so_state & SS_CANTRCVMORE) != 0 ||
4146c8f7fc3SBen Gras 	    so->so_qlen != 0 || so->so_error != 0;
4156c8f7fc3SBen Gras }
4166c8f7fc3SBen Gras 
4176c8f7fc3SBen Gras /* can we write something to so? */
4186c8f7fc3SBen Gras static inline int
sowritable(struct socket * so)4196c8f7fc3SBen Gras sowritable(struct socket *so)
4206c8f7fc3SBen Gras {
4216c8f7fc3SBen Gras 
4226c8f7fc3SBen Gras 	KASSERT(solocked(so));
4236c8f7fc3SBen Gras 
4246c8f7fc3SBen Gras 	return (sbspace(&so->so_snd) >= so->so_snd.sb_lowat &&
4256c8f7fc3SBen Gras 	    ((so->so_state & SS_ISCONNECTED) != 0 ||
4266c8f7fc3SBen Gras 	    (so->so_proto->pr_flags & PR_CONNREQUIRED) == 0)) ||
4276c8f7fc3SBen Gras 	    (so->so_state & SS_CANTSENDMORE) != 0 ||
4286c8f7fc3SBen Gras 	    so->so_error != 0;
4296c8f7fc3SBen Gras }
4306c8f7fc3SBen Gras 
4316c8f7fc3SBen Gras /* adjust counters in sb reflecting allocation of m */
4326c8f7fc3SBen Gras static inline void
sballoc(struct sockbuf * sb,struct mbuf * m)4336c8f7fc3SBen Gras sballoc(struct sockbuf *sb, struct mbuf *m)
4346c8f7fc3SBen Gras {
4356c8f7fc3SBen Gras 
4366c8f7fc3SBen Gras 	KASSERT(solocked(sb->sb_so));
4376c8f7fc3SBen Gras 
4386c8f7fc3SBen Gras 	sb->sb_cc += m->m_len;
4396c8f7fc3SBen Gras 	sb->sb_mbcnt += MSIZE;
4406c8f7fc3SBen Gras 	if (m->m_flags & M_EXT)
4416c8f7fc3SBen Gras 		sb->sb_mbcnt += m->m_ext.ext_size;
4426c8f7fc3SBen Gras }
4436c8f7fc3SBen Gras 
4446c8f7fc3SBen Gras /* adjust counters in sb reflecting freeing of m */
4456c8f7fc3SBen Gras static inline void
sbfree(struct sockbuf * sb,struct mbuf * m)4466c8f7fc3SBen Gras sbfree(struct sockbuf *sb, struct mbuf *m)
4476c8f7fc3SBen Gras {
4486c8f7fc3SBen Gras 
4496c8f7fc3SBen Gras 	KASSERT(solocked(sb->sb_so));
4506c8f7fc3SBen Gras 
4516c8f7fc3SBen Gras 	sb->sb_cc -= m->m_len;
4526c8f7fc3SBen Gras 	sb->sb_mbcnt -= MSIZE;
4536c8f7fc3SBen Gras 	if (m->m_flags & M_EXT)
4546c8f7fc3SBen Gras 		sb->sb_mbcnt -= m->m_ext.ext_size;
4556c8f7fc3SBen Gras }
4566c8f7fc3SBen Gras 
4576c8f7fc3SBen Gras static inline void
sorwakeup(struct socket * so)4586c8f7fc3SBen Gras sorwakeup(struct socket *so)
4596c8f7fc3SBen Gras {
4606c8f7fc3SBen Gras 
4616c8f7fc3SBen Gras 	KASSERT(solocked(so));
4626c8f7fc3SBen Gras 
4636c8f7fc3SBen Gras 	if (sb_notify(&so->so_rcv))
4646c8f7fc3SBen Gras 		sowakeup(so, &so->so_rcv, POLL_IN);
4656c8f7fc3SBen Gras }
4666c8f7fc3SBen Gras 
4676c8f7fc3SBen Gras static inline void
sowwakeup(struct socket * so)4686c8f7fc3SBen Gras sowwakeup(struct socket *so)
4696c8f7fc3SBen Gras {
4706c8f7fc3SBen Gras 
4716c8f7fc3SBen Gras 	KASSERT(solocked(so));
4726c8f7fc3SBen Gras 
4736c8f7fc3SBen Gras 	if (sb_notify(&so->so_snd))
4746c8f7fc3SBen Gras 		sowakeup(so, &so->so_snd, POLL_OUT);
4756c8f7fc3SBen Gras }
4766c8f7fc3SBen Gras 
4776c8f7fc3SBen Gras static inline void
solock(struct socket * so)4786c8f7fc3SBen Gras solock(struct socket *so)
4796c8f7fc3SBen Gras {
4806c8f7fc3SBen Gras 	kmutex_t *lock;
4816c8f7fc3SBen Gras 
4826c8f7fc3SBen Gras 	lock = so->so_lock;
4836c8f7fc3SBen Gras 	mutex_enter(lock);
4846c8f7fc3SBen Gras 	if (__predict_false(lock != so->so_lock))
4856c8f7fc3SBen Gras 		solockretry(so, lock);
4866c8f7fc3SBen Gras }
4876c8f7fc3SBen Gras 
4886c8f7fc3SBen Gras static inline void
sounlock(struct socket * so)4896c8f7fc3SBen Gras sounlock(struct socket *so)
4906c8f7fc3SBen Gras {
4916c8f7fc3SBen Gras 
4926c8f7fc3SBen Gras 	mutex_exit(so->so_lock);
4936c8f7fc3SBen Gras }
4946c8f7fc3SBen Gras 
4956c8f7fc3SBen Gras #ifdef SOCKBUF_DEBUG
4966c8f7fc3SBen Gras /*
4976c8f7fc3SBen Gras  * SBLASTRECORDCHK: check sb->sb_lastrecord is maintained correctly.
4986c8f7fc3SBen Gras  * SBLASTMBUFCHK: check sb->sb_mbtail is maintained correctly.
4996c8f7fc3SBen Gras  *
5006c8f7fc3SBen Gras  * => panic if the socket buffer is inconsistent.
5016c8f7fc3SBen Gras  * => 'where' is used for a panic message.
5026c8f7fc3SBen Gras  */
5036c8f7fc3SBen Gras void	sblastrecordchk(struct sockbuf *, const char *);
5046c8f7fc3SBen Gras #define	SBLASTRECORDCHK(sb, where)	sblastrecordchk((sb), (where))
5056c8f7fc3SBen Gras 
5066c8f7fc3SBen Gras void	sblastmbufchk(struct sockbuf *, const char *);
5076c8f7fc3SBen Gras #define	SBLASTMBUFCHK(sb, where)	sblastmbufchk((sb), (where))
5086c8f7fc3SBen Gras #define	SBCHECK(sb)			sbcheck(sb)
5096c8f7fc3SBen Gras #else
5106c8f7fc3SBen Gras #define	SBLASTRECORDCHK(sb, where)	/* nothing */
5116c8f7fc3SBen Gras #define	SBLASTMBUFCHK(sb, where)	/* nothing */
5126c8f7fc3SBen Gras #define	SBCHECK(sb)			/* nothing */
5136c8f7fc3SBen Gras #endif /* SOCKBUF_DEBUG */
5146c8f7fc3SBen Gras 
5156c8f7fc3SBen Gras /* sosend loan */
5166c8f7fc3SBen Gras vaddr_t	sokvaalloc(vaddr_t, vsize_t, struct socket *);
5176c8f7fc3SBen Gras void	sokvafree(vaddr_t, vsize_t);
5186c8f7fc3SBen Gras void	soloanfree(struct mbuf *, void *, size_t, void *);
5196c8f7fc3SBen Gras 
5206c8f7fc3SBen Gras /*
5216c8f7fc3SBen Gras  * Values for socket-buffer-append priority argument to sbappendaddrchain().
5226c8f7fc3SBen Gras  * The following flags are reserved for future implementation:
5236c8f7fc3SBen Gras  *
5246c8f7fc3SBen Gras  *  SB_PRIO_NONE:  honour normal socket-buffer limits.
5256c8f7fc3SBen Gras  *
5266c8f7fc3SBen Gras  *  SB_PRIO_ONESHOT_OVERFLOW:  if the socket has any space,
5276c8f7fc3SBen Gras  *	deliver the entire chain. Intended for large requests
5286c8f7fc3SBen Gras  *      that should be delivered in their entirety, or not at all.
5296c8f7fc3SBen Gras  *
5306c8f7fc3SBen Gras  * SB_PRIO_OVERDRAFT:  allow a small (2*MLEN) overflow, over and
5316c8f7fc3SBen Gras  *	aboce normal socket limits. Intended messages indicating
5326c8f7fc3SBen Gras  *      buffer overflow in earlier normal/lower-priority messages .
5336c8f7fc3SBen Gras  *
5346c8f7fc3SBen Gras  * SB_PRIO_BESTEFFORT: Ignore  limits entirely.  Intended only for
5356c8f7fc3SBen Gras  * 	kernel-generated messages to specially-marked scokets which
5366c8f7fc3SBen Gras  *	require "reliable" delivery, nd where the source socket/protocol
5376c8f7fc3SBen Gras  *	message generator enforce some hard limit (but possibly well
5386c8f7fc3SBen Gras  *	above kern.sbmax). It is entirely up to the in-kernel source to
5396c8f7fc3SBen Gras  *	avoid complete mbuf exhaustion or DoS scenarios.
5406c8f7fc3SBen Gras  */
5416c8f7fc3SBen Gras #define SB_PRIO_NONE 	 	0
5426c8f7fc3SBen Gras #define SB_PRIO_ONESHOT_OVERFLOW 1
5436c8f7fc3SBen Gras #define SB_PRIO_OVERDRAFT	2
5446c8f7fc3SBen Gras #define SB_PRIO_BESTEFFORT	3
5456c8f7fc3SBen Gras 
5466c8f7fc3SBen Gras /*
5476c8f7fc3SBen Gras  * Accept filter functions (duh).
5486c8f7fc3SBen Gras  */
5496c8f7fc3SBen Gras int	accept_filt_getopt(struct socket *, struct sockopt *);
5506c8f7fc3SBen Gras int	accept_filt_setopt(struct socket *, const struct sockopt *);
5516c8f7fc3SBen Gras int	accept_filt_clear(struct socket *);
5526c8f7fc3SBen Gras int	accept_filt_add(struct accept_filter *);
5536c8f7fc3SBen Gras int	accept_filt_del(struct accept_filter *);
5546c8f7fc3SBen Gras struct	accept_filter *accept_filt_get(char *);
5556c8f7fc3SBen Gras #ifdef ACCEPT_FILTER_MOD
5566c8f7fc3SBen Gras #ifdef SYSCTL_DECL
5576c8f7fc3SBen Gras SYSCTL_DECL(_net_inet_accf);
5586c8f7fc3SBen Gras #endif
5596c8f7fc3SBen Gras void	accept_filter_init(void);
5606c8f7fc3SBen Gras #endif
5616c8f7fc3SBen Gras 
5626c8f7fc3SBen Gras #endif /* _KERNEL */
5636c8f7fc3SBen Gras 
5646c8f7fc3SBen Gras #endif /* !_SYS_SOCKETVAR_H_ */
565