fixes for range locking
[unix-history] / usr / src / sys / deprecated / bbnnet / rdp_macros.h
CommitLineData
17efd7fe
MK
1/*
2 $Log: rdp_macros.h,v $
3 * Revision 2.6 84/11/14 13:24:53 walsh
4 * macro to go with monitoring outgoing packets on a debugged RDP connection.
5 *
6 * Revision 2.5 84/11/08 16:11:38 walsh
7 * Added code to gather statistics on RDP traffic. This makes the RDPCB
8 * too big unles you make mbufs 512 bytes large. RDP_CS should be turned off
9 * unless you do.
10 *
11 * Revision 2.4 84/11/05 15:53:21 walsh
12 * update_nulltimer() macro began to look inappropriate with recent
13 * changes, so its been stripped out and put in-line.
14 *
15 * Revision 2.3 84/11/05 14:24:45 walsh
16 * added comment.
17 *
18 * Revision 2.2 84/11/02 18:23:51 walsh
19 * Protocol specifiers want NULL message to have own sequence number in
20 * case of slow (t>NULL msg timeout) packets. I don't see this as a problem,
21 * and even if happened (dubious) would only delay discovery, but I
22 * didn't win this one. Initially not designed for this, but fixes are
23 * in almost neatly.
24 *
25 * Revision 2.1 84/11/02 10:13:25 walsh
26 * Fixed to include RCS comments in checked out source.
27 *
28 *
29 * description:
30 * Organized macros used by RDP and put most of them here.
31 *
32 * revision 1.3
33 * date: 84/07/19 13:53:16; author: walsh; state: Exp; lines added/del: 24/4
34 * worked on retransmit took too long macro. Should now advise
35 * sockets sleeping in connect(2) and does trash child sockets
36 * who cannot connect to their peers.
37 *
38 * revision 1.2
39 * date: 84/07/19 10:53:06; author: walsh; state: Exp; lines added/del: 8/5
40 * Changed retransmit took too long timer to be advisory in nature. It
41 * reports error to user, but does not affect connection state.
42 *
43 * revision 1.1
44 * date: 84/07/19 10:24:08; author: walsh; state: Exp;
45 * Initial revision
46 */
47
48
49/********** Macros to hide (socket) level above **********/
50
51/*
52 * The user notifies the RDP of the maximum sized datagram he's willing to
53 * receive by adjusting the socket receive buffering accordingly.
54 */
55#define pick_ourmaxlen(rdpcb) \
56 ((rdpcb)->r_ourmaxlen = (rdpcb)->r_inpcb->inp_socket->so_rcv.sb_hiwat)
57
58/*
59 * Notify user of error condition via the socket
60 */
61#define set_error(rdpcb, error) (rdpcb)->r_inpcb->inp_socket->so_error = error;
62
63/*
64 * On packet reception, can we q a datagram on the socket for the user?
65 * We only q one on the socket at a time.
66 */
67#define usr_rbuf_is_empty(rdpcb) \
68 ((rdpcb)->r_inpcb->inp_socket->so_rcv.sb_cc == 0)
69
70/*
71 * All the datagrams are buffered by RDP. RDP has reached its buffering
72 * limit, so prevent the user from queueing more up until we get some
73 * acknowledgements back from the other side.
74 */
75#define sendbufisfull(rdpcb) \
76 { struct sockbuf *sosnd; \
77 sosnd = &(rdpcb)->r_inpcb->inp_socket->so_snd; \
78 sosnd->sb_cc = sosnd->sb_hiwat; \
79 }
80
81/*
82 * Permit the user to q up more datagrams for sending.
83 *
84 * We only need to wake up a writer if he's blocked for
85 * buffering space. RDP allows at most 1 datagram in
86 * the socket code, and no datagrams for transmission
87 * are stored on the socket due to RDP's messing with
88 * so_snd.sb_cc, so we are able to do the wakeup iff necessary
89 */
90#define sendbufhasspace(rdpcb) \
91 { struct socket *so; \
92 so = (rdpcb)->r_inpcb->inp_socket; \
93 if (so->so_snd.sb_cc) { \
94 so->so_snd.sb_cc = 0; \
95 sowwakeup(so); \
96 }}
97
98#define wakeup_reader(rdpcb) sorwakeup((rdpcb)->r_inpcb->inp_socket)
99#define wakeup_writer(rdpcb) sowwakeup((rdpcb)->r_inpcb->inp_socket)
100
101/*
102 * We can't send any new datagrams after we've been reset.
103 */
104#define user_cantsendmore(rdpcb) socantsendmore((rdpcb)->r_inpcb->inp_socket)
105
106#define user_cantreadmore(rdpcb) socantrcvmore((rdpcb)->r_inpcb->inp_socket)
107
108/*
109 * The socket code prevents read(2) or write(2) until we're connected to
110 * the other end. Nor can a child socket be accept(2)ed until the connection
111 * is established.
112 */
113#define rdpisconnected(rdpcb) soisconnected((rdpcb)->r_inpcb->inp_socket)
114
115
116/********** Macros to save duplicating code fragments **********/
117
118/*
119 * set up re-transmission timer for packet we just sent.
120 */
121#define set_rxtimer(rdpcb, N) \
122 { (rdpcb)->r_rxtimers[N] = (rdpcb)->r_rxmitime; \
123 (rdpcb)->r_timers[RDP_tRXMIT] = RDP_tvRXCHECK; \
124 if ((rdpcb)->r_rttlindex < 0) { \
125 (rdpcb)->r_rttlindex = N; \
126 (rdpcb)->r_timers[RDP_tRTTL] = (rdpcb)->r_rttl; \
127 } }
128
129/*
130 * we received the other guy's SYN, and it was in packet seqnum
131 */
132#define got_syn(rdpcb, seqnum) \
133 { (rdpcb)->r_synrcvd = TRUE; \
134 (rdpcb)->r_rcvq.rq_baseseq = (seqnum) +1; \
135 (rdpcb)->r_irs = seqnum; \
136 }
137
138/*
139 * RFC 908 section 3.5 page 16 says to use twice the advertised buffering
140 * This is a bad idea that is an attempt to make up for network latency
141 * and to try to keep things pipelined. We'll use only advertised buffering.
142 * Approach: Don't make trouble, other end must ask for it. (by
143 * advertising more than has)
144 */
145#define process_synopt(rdpcb, synopt) \
146 { (rdpcb)->r_hisnbuf = MAX(1, MIN (ntohs((u_short)(synopt)->rh_nbuf), \
147 RDP_MAXDGRAMS)); \
148 (rdpcb)->r_hismaxlen = ntohs((u_short)(synopt)->rh_maxlen); \
149 (rdpcb)->r_sequential = (rdpcb)->r_sequential || \
150 (ntohs((u_short)(synopt)->rh_options) & RDP_oSEQUENTIAL); \
151 sbreserve(&((rdpcb)->r_inpcb->inp_socket->so_snd), \
152 (rdpcb)->r_hismaxlen - HDRSLOP); \
153 }
154
155/*
156 * Advisory and does not close connection. Allows user to pick up any
157 * q'd received datagrams. But, if there's no host-host communications
158 * then these probably aren't useful. The real reason for advisory nature
159 * is that the user process knows best what to do, having contextual info.
160 * ??? break this up into specific code in state timeout functions ???
161 *
162 * RTTL occurs for 1) normal user datagrams, and 2) NULL messages
163 */
164#define rttl(rdpcb) \
165 { struct socket *rttlso; \
166 \
167 rttlso = (rdpcb)->r_inpcb->inp_socket; \
168 if (rttlso->so_state & SS_NOFDREF) \
169 /* \
170 * was a child socket of a listen(2)er trying to \
171 * establish connection with other end. RDP_sLSYNRCVD \
172 */ \
173 trash_pcbs(rdpcb); \
174 else { \
175 set_error(rdpcb, ETIMEDOUT); \
176 /* \
177 * sleeping in connect(2) and not using NBIO. \
178 * RDP_sSYNSENT (syn not acked yet) \
179 */ \
180 wakeup((caddr_t) &rttlso->so_timeo); \
181 /* \
182 * sleeping in write(2) waiting for buffer space \
183 * or sleeping in select(2). RDP_sESTAB \
184 */ \
185 wakeup_writer(rdpcb); \
186 /* \
187 * sleeping in read(2) for datagram from other side \
188 * and NULL msgs imply connection lost RDP_sESTAB \
189 */ \
190 wakeup_reader(rdpcb); \
191 (rdpcb)->r_timers[RDP_tRTTL] = (rdpcb)->r_rttl; \
192 }}
193
194/*
195 * Pass datagram to user.
196 * On UNIX, mark end of datagram by setting m_act on last mbuf in chain.
197 */
198#define usr_rbuf_append(rdpcb, m) \
199 { MBUF *x; \
200 for (x = (m); x->m_next; x = x->m_next) \
201 ; \
202 x->m_act = ((MBUF *) 1); \
203 sbappend(&(rdpcb)->r_inpcb->inp_socket->so_rcv, m); \
204 }
205
206/*
207 * For in-line coding of the state transition function.
208 */
209#ifdef RDP_CS
210#define RDP_ACTION1 (rdpcb)->r_entered[newstate] = iptime();
211#else
212#define RDP_ACTION1 /**/
213#endif
214
215#define debug_rdpcb(r) ((r)->r_inpcb->inp_socket->so_options & SO_DEBUG)
216
217#define RDP_ACTION(input, rdpcb, arg, newstate) \
218 { int (*func)(); \
219\
220 func = rdp_action_table[(rdpcb)->r_state][input]; \
221 if (! func){ \
222 /* \
223 * invalid state transition, just print a message and ignore \
224 */ \
225 printf("rdp bad transition: rdpcb 0x%x state %d input %d\n", \
226 (rdpcb), (rdpcb)->r_state, (input)); \
227 if (arg && (input == RDP_iNETR)) \
228 m_freem(dtom(arg)); \
229 newstate = RDP_sSAME; \
230 } else { \
231 boolean debug_on; \
232\
233 debug_on = debug_rdpcb(rdpcb); \
234 newstate = (*func)(rdpcb, arg); \
235 if (debug_on) \
236 rdp_debug (rdpcb, arg, input, newstate); \
237\
238 /* \
239 * No longer have mbufs for protocol control blocks if closed \
240 */ \
241 if ((newstate != RDP_sSAME) && (newstate != RDP_sCLOSED)){ \
242 rdpcb->r_state = newstate; \
243 RDP_ACTION1 \
244 } } }
245