clean out printf
[unix-history] / usr / src / sys / netinet / tcp_usrreq.c
CommitLineData
be43ac7f 1/* tcp_usrreq.c 1.41 81/12/12 */
72f24d7d 2
4eb5d593 3#include "../h/param.h"
72f24d7d 4#include "../h/systm.h"
dad64fdf
BJ
5#include "../h/mbuf.h"
6#include "../h/socket.h"
eee3ab16
BJ
7#include "../h/socketvar.h"
8#include "../h/protosw.h"
0974b45c
BJ
9#include "../net/in.h"
10#include "../net/in_pcb.h"
11#include "../net/in_systm.h"
4ad99bae 12#include "../net/if.h"
eee3ab16 13#include "../net/ip.h"
eb44bfb2 14#include "../net/ip_var.h"
eee3ab16 15#include "../net/tcp.h"
eee3ab16 16#include "../net/tcp_fsm.h"
0974b45c
BJ
17#include "../net/tcp_seq.h"
18#include "../net/tcp_timer.h"
eee3ab16 19#include "../net/tcp_var.h"
0974b45c 20#include "../net/tcpip.h"
f1b2fa5b 21#include "../errno.h"
eee3ab16 22
4aed14e3 23extern char *tcpstates[];
4ad99bae 24struct tcpcb *tcp_newtcpcb();
9c5022e3
BJ
25/*
26 * Process a TCP user request for tcp tb. If this is a send request
27 * then m is the mbuf chain of send data. If this is a timer expiration
28 * (called from the software clock routine), then timertype tells which timer.
29 */
eee3ab16
BJ
30tcp_usrreq(so, req, m, addr)
31 struct socket *so;
32 int req;
9c5022e3 33 struct mbuf *m;
eee3ab16 34 caddr_t addr;
4eb5d593 35{
53a5409e 36 register struct inpcb *inp = sotoinpcb(so);
cdad2eb1 37 register struct tcpcb *tp;
72f24d7d 38 int s = splnet();
eee3ab16 39 int error = 0;
72f24d7d
BJ
40COUNT(TCP_USRREQ);
41
53a5409e
BJ
42 /*
43 * Make sure attached. If not,
44 * only PRU_ATTACH is valid.
45 */
0974b45c 46 if (inp == 0 && req != PRU_ATTACH) {
a6503abf
BJ
47 splx(s);
48 return (EINVAL);
49 }
50 if (inp) {
cdad2eb1 51 tp = intotcpcb(inp);
9c5022e3 52#ifdef KPROF
a6503abf 53 tcp_acounts[tp->t_state][req]++;
9c5022e3 54#endif
cdad2eb1 55 }
eee3ab16 56 switch (req) {
4eb5d593 57
eee3ab16 58 case PRU_ATTACH:
4ad99bae 59 if (inp) {
eee3ab16 60 error = EISCONN;
cdad2eb1 61 break;
53a5409e 62 }
405c9168 63 error = in_pcbattach(so, &tcb, 2048, 2048, (struct sockaddr_in *)addr);
a6503abf 64 if (error)
4ad99bae 65 break;
4ad99bae 66 inp = (struct inpcb *)so->so_pcb;
4aed14e3 67 tp = tcp_newtcpcb(inp);
9190426d 68 if (so->so_options & SO_ACCEPTCONN) {
9190426d 69 if (tp == 0) {
405c9168 70 in_pcbdetach(inp);
9190426d
BJ
71 error = ENOBUFS;
72 break;
73 }
a6503abf 74 tp->t_state = TCPS_LISTEN;
9190426d 75 } else
a6503abf 76 tp->t_state = TCPS_CLOSED;
72f24d7d 77 break;
4eb5d593 78
eee3ab16 79 case PRU_DETACH:
405c9168 80 in_pcbdetach(inp);
eee3ab16
BJ
81 break;
82
eee3ab16 83 case PRU_CONNECT:
405c9168 84 error = in_pcbconnect(inp, (struct sockaddr_in *)addr);
4ad99bae 85 if (error)
53a5409e 86 break;
9190426d 87 tp = tcp_newtcpcb(inp);
4aed14e3
BJ
88 if (tp == 0)
89 goto badcon;
b454c3ea 90 tp->t_template = tcp_template(tp);
4aed14e3
BJ
91 if (tp->t_template == 0)
92 goto badcon2;
9190426d
BJ
93 tp->t_inpcb = inp;
94 inp->inp_ppcb = (caddr_t)tp;
53a5409e 95 soisconnecting(so);
a6503abf 96 tp->t_state = TCPS_SYN_SENT;
4aed14e3
BJ
97 tp->t_timer[TCPT_KEEP] = TCPTV_KEEP;
98 tp->iss = tcp_iss; tcp_iss += TCP_ISSINCR/2;
99 tcp_sendseqinit(tp);
f1b2fa5b 100 (void) tcp_output(tp);
72f24d7d 101 break;
4eb5d593 102
4aed14e3
BJ
103badcon2:
104 (void) m_free(dtom(tp));
105badcon:
106 in_pcbdisconnect(inp);
107 error = ENOBUFS;
108 break;
109
2b4b57cd 110 case PRU_ACCEPT:
4ad99bae
BJ
111 soisconnected(so);
112 break;
2b4b57cd 113
eee3ab16 114 case PRU_DISCONNECT:
a6503abf
BJ
115 if (tp->t_state < TCPS_ESTABLISHED)
116 tcp_close(tp);
53a5409e 117 else {
53a5409e 118 soisdisconnecting(so);
4aed14e3 119 tcp_usrclosed(tp);
f1b2fa5b 120 (void) tcp_output(tp);
53a5409e 121 }
eee3ab16
BJ
122 break;
123
eee3ab16 124 case PRU_SHUTDOWN:
0974b45c 125 socantsendmore(so);
4aed14e3
BJ
126 tcp_usrclosed(tp);
127 (void) tcp_output(tp);
72f24d7d
BJ
128 break;
129
eee3ab16 130 case PRU_RCVD:
f1b2fa5b 131 (void) tcp_output(tp);
72f24d7d
BJ
132 break;
133
eee3ab16 134 case PRU_SEND:
a6503abf 135 sbappend(&so->so_snd, m);
0974b45c
BJ
136/*
137 if (tp->t_flags & TF_PUSH)
a6503abf 138 tp->snd_end = tp->snd_una + so->so_snd.sb_cc;
0974b45c
BJ
139 */
140 if (tp->t_flags & TF_URG)
141 tp->snd_up = tp->snd_una + so->so_snd.sb_cc + 1;
f1b2fa5b 142 (void) tcp_output(tp);
72f24d7d
BJ
143 break;
144
eee3ab16 145 case PRU_ABORT:
a6503abf 146 tcp_drop(tp, ECONNABORTED);
72f24d7d
BJ
147 break;
148
eee3ab16 149 case PRU_CONTROL:
53a5409e 150 error = EOPNOTSUPP;
eee3ab16
BJ
151 break;
152
f1b2fa5b
BJ
153 case PRU_SENSE:
154 error = EOPNOTSUPP;
155 break;
156
157 case PRU_RCVOOB:
158 error = EOPNOTSUPP;
159 break;
160
161 case PRU_SENDOOB:
162 error = EOPNOTSUPP;
163 break;
164
eee3ab16 165 case PRU_SLOWTIMO:
a6503abf 166 tcp_timers(tp, (int)addr);
eee3ab16
BJ
167 break;
168
9c5022e3
BJ
169 default:
170 panic("tcp_usrreq");
72f24d7d
BJ
171 }
172 splx(s);
53a5409e 173 return (error);
4eb5d593 174}
4aed14e3 175
4aed14e3
BJ
176tcp_usrclosed(tp)
177 struct tcpcb *tp;
178{
179
4aed14e3
BJ
180 switch (tp->t_state) {
181
182 case TCPS_LISTEN:
183 case TCPS_SYN_SENT:
184 tp->t_state = TCPS_CLOSED;
185 tcp_close(tp);
186 break;
187
188 case TCPS_SYN_RECEIVED:
189 case TCPS_ESTABLISHED:
190 tp->t_state = TCPS_FIN_WAIT_1;
191 break;
192
193 case TCPS_CLOSE_WAIT:
194 tp->t_state = TCPS_LAST_ACK;
195 break;
196 }
4aed14e3 197}