xref: /csrg-svn/sys/kern/sys_socket.c (revision 47540)
123386Smckusick /*
240935Skarels  * Copyright (c) 1982, 1986, 1990 Regents of the University of California.
333921Sbostic  * All rights reserved.
423386Smckusick  *
544445Sbostic  * %sccs.include.redist.c%
633921Sbostic  *
7*47540Skarels  *	@(#)sys_socket.c	7.9 (Berkeley) 03/17/91
823386Smckusick  */
912794Ssam 
1017095Sbloom #include "param.h"
1117095Sbloom #include "systm.h"
1217095Sbloom #include "user.h"
1317095Sbloom #include "file.h"
1417095Sbloom #include "mbuf.h"
1517095Sbloom #include "protosw.h"
1617095Sbloom #include "socket.h"
1717095Sbloom #include "socketvar.h"
1817095Sbloom #include "ioctl.h"
1917095Sbloom #include "uio.h"
2017095Sbloom #include "stat.h"
2112794Ssam 
2212794Ssam #include "../net/if.h"
2312794Ssam #include "../net/route.h"
2412794Ssam 
2537728Smckusick int	soo_read(), soo_write(), soo_ioctl(), soo_select(), soo_close();
2612794Ssam struct	fileops socketops =
2737728Smckusick     { soo_read, soo_write, soo_ioctl, soo_select, soo_close };
2812794Ssam 
2937728Smckusick /* ARGSUSED */
3037728Smckusick soo_read(fp, uio, cred)
3112794Ssam 	struct file *fp;
3212794Ssam 	struct uio *uio;
3337728Smckusick 	struct ucred *cred;
3412794Ssam {
3512794Ssam 
3637728Smckusick 	return (soreceive((struct socket *)fp->f_data, (struct mbuf **)0,
3740935Skarels 		uio, (struct mbuf **)0, (struct mbuf **)0, (int *)0));
3812794Ssam }
3912794Ssam 
4037728Smckusick /* ARGSUSED */
4137728Smckusick soo_write(fp, uio, cred)
4237728Smckusick 	struct file *fp;
4337728Smckusick 	struct uio *uio;
4437728Smckusick 	struct ucred *cred;
4537728Smckusick {
4637728Smckusick 
4737728Smckusick 	return (sosend((struct socket *)fp->f_data, (struct mbuf *)0,
4840935Skarels 		uio, (struct mbuf *)0, (struct mbuf *)0, 0));
4937728Smckusick }
5037728Smckusick 
51*47540Skarels soo_ioctl(fp, cmd, data, p)
5212794Ssam 	struct file *fp;
5312794Ssam 	int cmd;
5412794Ssam 	register caddr_t data;
55*47540Skarels 	struct proc *p;
5612794Ssam {
5712794Ssam 	register struct socket *so = (struct socket *)fp->f_data;
5812794Ssam 
5912794Ssam 	switch (cmd) {
6012794Ssam 
6112794Ssam 	case FIONBIO:
6212794Ssam 		if (*(int *)data)
6312794Ssam 			so->so_state |= SS_NBIO;
6412794Ssam 		else
6512794Ssam 			so->so_state &= ~SS_NBIO;
6613050Ssam 		return (0);
6712794Ssam 
6812794Ssam 	case FIOASYNC:
6943897Skarels 		if (*(int *)data) {
7012794Ssam 			so->so_state |= SS_ASYNC;
7143897Skarels 			so->so_rcv.sb_flags |= SB_ASYNC;
7243897Skarels 			so->so_snd.sb_flags |= SB_ASYNC;
7343897Skarels 		} else {
7412794Ssam 			so->so_state &= ~SS_ASYNC;
7543897Skarels 			so->so_rcv.sb_flags &= ~SB_ASYNC;
7643897Skarels 			so->so_snd.sb_flags &= ~SB_ASYNC;
7743897Skarels 		}
7813050Ssam 		return (0);
7912794Ssam 
8013001Ssam 	case FIONREAD:
8113001Ssam 		*(int *)data = so->so_rcv.sb_cc;
8213050Ssam 		return (0);
8313001Ssam 
8412794Ssam 	case SIOCSPGRP:
8537478Ssklower 		so->so_pgid = *(int *)data;
8613050Ssam 		return (0);
8712794Ssam 
8812794Ssam 	case SIOCGPGRP:
8937478Ssklower 		*(int *)data = so->so_pgid;
9013050Ssam 		return (0);
9112794Ssam 
9212794Ssam 	case SIOCATMARK:
9312794Ssam 		*(int *)data = (so->so_state&SS_RCVATMARK) != 0;
9413050Ssam 		return (0);
9512794Ssam 	}
9613050Ssam 	/*
9713050Ssam 	 * Interface/routing/protocol specific ioctls:
9813050Ssam 	 * interface and routing ioctls should have a
9913050Ssam 	 * different entry since a socket's unnecessary
10013050Ssam 	 */
10140935Skarels 	if (IOCGROUP(cmd) == 'i')
102*47540Skarels 		return (ifioctl(so, cmd, data, p));
10340935Skarels 	if (IOCGROUP(cmd) == 'r')
104*47540Skarels 		return (rtioctl(cmd, data, p));
10513050Ssam 	return ((*so->so_proto->pr_usrreq)(so, PRU_CONTROL,
10613050Ssam 	    (struct mbuf *)cmd, (struct mbuf *)data, (struct mbuf *)0));
10712794Ssam }
10812794Ssam 
109*47540Skarels soo_select(fp, which, p)
11012794Ssam 	struct file *fp;
11112794Ssam 	int which;
112*47540Skarels 	struct proc *p;
11312794Ssam {
11412794Ssam 	register struct socket *so = (struct socket *)fp->f_data;
11512794Ssam 	register int s = splnet();
11612794Ssam 
11712794Ssam 	switch (which) {
11812794Ssam 
11912794Ssam 	case FREAD:
12012794Ssam 		if (soreadable(so)) {
12112794Ssam 			splx(s);
12212794Ssam 			return (1);
12312794Ssam 		}
124*47540Skarels 		sbselqueue(&so->so_rcv, p);
12512794Ssam 		break;
12612794Ssam 
12712794Ssam 	case FWRITE:
12812794Ssam 		if (sowriteable(so)) {
12912794Ssam 			splx(s);
13012794Ssam 			return (1);
13112794Ssam 		}
132*47540Skarels 		sbselqueue(&so->so_snd, p);
13312794Ssam 		break;
13424768Skarels 
13524768Skarels 	case 0:
13624768Skarels 		if (so->so_oobmark ||
13724768Skarels 		    (so->so_state & SS_RCVATMARK)) {
13824768Skarels 			splx(s);
13924768Skarels 			return (1);
14024768Skarels 		}
141*47540Skarels 		sbselqueue(&so->so_rcv, p);
14224768Skarels 		break;
14312794Ssam 	}
14412794Ssam 	splx(s);
14512794Ssam 	return (0);
14612794Ssam }
14712794Ssam 
14813045Ssam soo_stat(so, ub)
14913045Ssam 	register struct socket *so;
15012794Ssam 	register struct stat *ub;
15112794Ssam {
15212794Ssam 
15312794Ssam 	bzero((caddr_t)ub, sizeof (*ub));
15412794Ssam 	return ((*so->so_proto->pr_usrreq)(so, PRU_SENSE,
15512794Ssam 	    (struct mbuf *)ub, (struct mbuf *)0,
15612794Ssam 	    (struct mbuf *)0));
15712794Ssam }
15812794Ssam 
15912794Ssam soo_close(fp)
16012794Ssam 	struct file *fp;
16112794Ssam {
16214032Ssam 	int error = 0;
16333921Sbostic 
16414032Ssam 	if (fp->f_data)
16514032Ssam 		error = soclose((struct socket *)fp->f_data);
16612794Ssam 	fp->f_data = 0;
16712794Ssam 	return (error);
16812794Ssam }
169