Nuke compatiblity parts.
[dragonfly.git] / sys / net / i4b / layer2 / i4b_l2fsm.c
1 /*
2  * Copyright (c) 1997, 2000 Hellmuth Michaelis. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
14  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
16  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
17  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
18  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
19  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
20  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
21  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
22  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
23  * SUCH DAMAGE.
24  *
25  *---------------------------------------------------------------------------
26  *
27  *      i4b_l2fsm.c - layer 2 FSM
28  *      -------------------------
29  *
30  *      $Id: i4b_l2fsm.c,v 1.22 2000/08/24 11:48:58 hm Exp $ 
31  *
32  * $FreeBSD: src/sys/i4b/layer2/i4b_l2fsm.c,v 1.6.2.1 2001/08/10 14:08:41 obrien Exp $
33  * $DragonFly: src/sys/net/i4b/layer2/i4b_l2fsm.c,v 1.6 2005/06/14 21:19:19 joerg Exp $
34  *
35  *      last edit-date: [Tue May 30 15:48:20 2000]
36  *
37  *---------------------------------------------------------------------------*/
38
39 #include "use_i4bq921.h"
40 #if NI4BQ921 > 0
41
42 #include <sys/param.h>
43 #include <sys/systm.h>
44 #include <sys/socket.h>
45 #include <net/if.h>
46
47 #include <net/i4b/include/machine/i4b_debug.h>
48 #include <net/i4b/include/machine/i4b_ioctl.h>
49
50 #include "../include/i4b_global.h"
51 #include "../include/i4b_l2l3.h"
52 #include "../include/i4b_mbuf.h"
53
54 #include "i4b_l2.h"
55 #include "i4b_l2fsm.h"
56
57 l2_softc_t l2_softc[MAXL1UNITS];
58
59 #if DO_I4B_DEBUG
60 static char *l2state_text[N_STATES] = {
61         "ST_TEI_UNAS",
62         "ST_ASG_AW_TEI",
63         "ST_EST_AW_TEI",
64         "ST_TEI_ASGD",
65
66         "ST_AW_EST",
67         "ST_AW_REL",
68         "ST_MULTIFR",
69         "ST_TIMREC",
70
71         "ST_SUBSET",
72         "Illegal State"
73 };
74
75 static char *l2event_text[N_EVENTS] = {
76         "EV_DLESTRQ",
77         "EV_DLUDTRQ",
78         "EV_MDASGRQ",
79         "EV_MDERRRS",
80         "EV_PSDEACT",
81         "EV_MDREMRQ",
82         "EV_RXSABME",
83         "EV_RXDISC",
84         "EV_RXUA",
85         "EV_RXDM",
86         "EV_T200EXP",
87         "EV_DLDATRQ",
88         "EV_DLRELRQ",
89         "EV_T203EXP",
90         "EV_OWNBUSY",
91         "EV_OWNRDY", 
92         "EV_RXRR",
93         "EV_RXREJ",
94         "EV_RXRNR",
95         "EV_RXFRMR",
96         "Illegal Event"
97 };
98 #endif
99
100 static void F_TU01 (l2_softc_t *);
101 static void F_TU03 (l2_softc_t *);
102
103 static void F_TA03 (l2_softc_t *);
104 static void F_TA04 (l2_softc_t *);
105 static void F_TA05 (l2_softc_t *);
106
107 static void F_TE03 (l2_softc_t *);
108 static void F_TE04 (l2_softc_t *);
109 static void F_TE05 (l2_softc_t *);
110
111 static void F_T01 (l2_softc_t *);
112 static void F_T05 (l2_softc_t *);
113 static void F_T06 (l2_softc_t *);
114 static void F_T07 (l2_softc_t *);
115 static void F_T08 (l2_softc_t *);
116 static void F_T09 (l2_softc_t *);
117 static void F_T10 (l2_softc_t *);
118 static void F_T13 (l2_softc_t *);
119
120 static void F_AE01 (l2_softc_t *);
121 static void F_AE05 (l2_softc_t *);
122 static void F_AE06 (l2_softc_t *);
123 static void F_AE07 (l2_softc_t *);
124 static void F_AE08 (l2_softc_t *);
125 static void F_AE09 (l2_softc_t *);
126 static void F_AE10 (l2_softc_t *);
127 static void F_AE11 (l2_softc_t *);
128 static void F_AE12 (l2_softc_t *);
129
130 static void F_AR05 (l2_softc_t *);
131 static void F_AR06 (l2_softc_t *);
132 static void F_AR07 (l2_softc_t *);
133 static void F_AR08 (l2_softc_t *);
134 static void F_AR09 (l2_softc_t *);
135 static void F_AR10 (l2_softc_t *);
136 static void F_AR11 (l2_softc_t *);
137
138 static void F_MF01 (l2_softc_t *);
139 static void F_MF05 (l2_softc_t *);
140 static void F_MF06 (l2_softc_t *);
141 static void F_MF07 (l2_softc_t *);
142 static void F_MF08 (l2_softc_t *);
143 static void F_MF09 (l2_softc_t *);
144 static void F_MF10 (l2_softc_t *);
145 static void F_MF11 (l2_softc_t *);
146 static void F_MF12 (l2_softc_t *);
147 static void F_MF13 (l2_softc_t *);
148 static void F_MF14 (l2_softc_t *);
149 static void F_MF15 (l2_softc_t *);
150 static void F_MF16 (l2_softc_t *);
151 static void F_MF17 (l2_softc_t *);
152 static void F_MF18 (l2_softc_t *);
153 static void F_MF19 (l2_softc_t *);
154 static void F_MF20 (l2_softc_t *);
155
156 static void F_TR01 (l2_softc_t *);
157 static void F_TR05 (l2_softc_t *);
158 static void F_TR06 (l2_softc_t *);
159 static void F_TR07 (l2_softc_t *);
160 static void F_TR08 (l2_softc_t *);
161 static void F_TR09 (l2_softc_t *);
162 static void F_TR10 (l2_softc_t *);
163 static void F_TR11 (l2_softc_t *);
164 static void F_TR12 (l2_softc_t *);
165 static void F_TR13 (l2_softc_t *);
166 static void F_TR15 (l2_softc_t *);
167 static void F_TR16 (l2_softc_t *);
168 static void F_TR17 (l2_softc_t *);
169 static void F_TR18 (l2_softc_t *);
170 static void F_TR19 (l2_softc_t *);
171 static void F_TR20 (l2_softc_t *);
172 static void F_ILL (l2_softc_t *);
173 static void F_NCNA (l2_softc_t *);
174
175 /*---------------------------------------------------------------------------*
176  *      FSM illegal state default action
177  *---------------------------------------------------------------------------*/ 
178 static void
179 F_ILL(l2_softc_t *l2sc)
180 {
181         NDBGL2(L2_F_ERR, "FSM function F_ILL executing");
182 }
183
184 /*---------------------------------------------------------------------------*
185  *      FSM No change, No action
186  *---------------------------------------------------------------------------*/ 
187 static void
188 F_NCNA(l2_softc_t *l2sc)
189 {
190         NDBGL2(L2_F_MSG, "FSM function F_NCNA executing");
191 }
192
193 /*---------------------------------------------------------------------------*
194  *      layer 2 state transition table
195  *---------------------------------------------------------------------------*/ 
196 struct l2state_tab {
197         void (*func) (l2_softc_t *);    /* function to execute */
198         int newstate;                           /* next state */
199 } l2state_tab[N_EVENTS][N_STATES] = {
200
201 /* STATE:       ST_TEI_UNAS,                    ST_ASG_AW_TEI,                  ST_EST_AW_TEI,                  ST_TEI_ASGD,            ST_AW_EST,              ST_AW_REL,              ST_MULTIFR,             ST_TIMREC,              ST_SUBSET,              ILLEGAL STATE   */
202 /* -----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
203 /*EV_DLESTRQ*/{ {F_TU01, ST_EST_AW_TEI},        {F_NCNA, ST_EST_AW_TEI},        {F_ILL, ST_ILL},                {F_T01, ST_AW_EST},     {F_AE01, ST_AW_EST},    {F_ILL, ST_ILL},        {F_MF01, ST_AW_EST},    {F_TR01, ST_AW_EST},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
204 /*EV_DLUDTRQ*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
205 /*EV_MDASGRQ*/{ {F_TU03, ST_TEI_ASGD},          {F_TA03, ST_TEI_ASGD},          {F_TE03, ST_AW_EST},            {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
206 /*EV_MDERRRS*/{ {F_ILL, ST_ILL},                {F_TA04, ST_TEI_UNAS},          {F_TE04, ST_TEI_UNAS},          {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
207 /*EV_PSDEACT*/{ {F_ILL, ST_ILL},                {F_TA05, ST_TEI_UNAS},          {F_TE05, ST_TEI_UNAS},          {F_T05, ST_TEI_ASGD},   {F_AE05, ST_TEI_ASGD},  {F_AR05, ST_TEI_ASGD},  {F_MF05, ST_TEI_ASGD},  {F_TR05, ST_TEI_ASGD},  {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
208 /*EV_MDREMRQ*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_T06, ST_TEI_UNAS},   {F_AE06, ST_TEI_UNAS},  {F_AR06, ST_TEI_UNAS},  {F_MF06, ST_TEI_UNAS},  {F_TR06, ST_TEI_UNAS},  {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
209 /*EV_RXSABME*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_T07, ST_SUBSET},     {F_AE07, ST_AW_EST},    {F_AR07, ST_AW_REL},    {F_MF07, ST_MULTIFR},   {F_TR07, ST_MULTIFR},   {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
210 /*EV_RXDISC */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_T08, ST_TEI_ASGD},   {F_AE08, ST_AW_EST},    {F_AR08, ST_AW_REL},    {F_MF08, ST_TEI_ASGD},  {F_TR08, ST_TEI_ASGD},  {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
211 /*EV_RXUA   */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_T09, ST_TEI_ASGD},   {F_AE09, ST_SUBSET},    {F_AR09, ST_SUBSET},    {F_MF09, ST_MULTIFR},   {F_TR09, ST_TIMREC},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
212 /*EV_RXDM   */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_T10, ST_SUBSET},     {F_AE10, ST_SUBSET},    {F_AR10, ST_SUBSET},    {F_MF10, ST_SUBSET},    {F_TR10, ST_AW_EST},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
213 /*EV_T200EXP*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_AE11, ST_SUBSET},    {F_AR11, ST_SUBSET},    {F_MF11, ST_TIMREC},    {F_TR11, ST_SUBSET},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
214 /*EV_DLDATRQ*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_AE12, ST_AW_EST},    {F_ILL, ST_ILL},        {F_MF12, ST_MULTIFR},   {F_TR12, ST_TIMREC},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
215 /*EV_DLRELRQ*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_T13, ST_TEI_ASGD},   {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF13, ST_AW_REL},    {F_TR13, ST_AW_REL},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
216 /*EV_T203EXP*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF14, ST_TIMREC},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
217 /*EV_OWNBUSY*/{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF15, ST_MULTIFR},   {F_TR15, ST_TIMREC},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
218 /*EV_OWNRDY */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF16, ST_MULTIFR},   {F_TR16, ST_TIMREC},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
219 /*EV_RXRR   */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF17, ST_SUBSET},    {F_TR17, ST_SUBSET},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
220 /*EV_RXREJ  */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF18, ST_SUBSET},    {F_TR18, ST_SUBSET},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
221 /*EV_RXRNR  */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF19, ST_SUBSET},    {F_TR19, ST_SUBSET},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
222 /*EV_RXFRMR */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_MF20, ST_AW_EST},    {F_TR20, ST_AW_EST},    {F_ILL, ST_ILL},        {F_ILL, ST_ILL} },
223 /*EV_ILL    */{ {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},                {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL},        {F_ILL, ST_ILL} }
224 };
225
226 /*---------------------------------------------------------------------------*
227  *      event handler, executes function and sets new state
228  *---------------------------------------------------------------------------*/ 
229 void i4b_next_l2state(l2_softc_t *l2sc, int event)
230 {
231         int currstate, newstate;
232         int (*savpostfsmfunc)(int) = NULL;
233
234         /* check event number */
235         if(event > N_EVENTS)
236                 panic("i4b_l2fsm.c: event > N_EVENTS\n");
237
238         /* get current state and check it */
239         if((currstate = l2sc->Q921_state) > N_STATES)   /* failsafe */
240                 panic("i4b_l2fsm.c: currstate > N_STATES\n");   
241
242         /* get new state and check it */
243         if((newstate = l2state_tab[event][currstate].newstate) > N_STATES)
244                 panic("i4b_l2fsm.c: newstate > N_STATES\n");    
245         
246         
247         if(newstate != ST_SUBSET)
248         {       /* state function does NOT set new state */
249                 NDBGL2(L2_F_MSG, "FSM event [%s]: [%s/%d => %s/%d]",
250                                 l2event_text[event],
251                                 l2state_text[currstate], currstate,
252                                 l2state_text[newstate], newstate);
253         }
254
255         /* execute state transition function */
256         (*l2state_tab[event][currstate].func)(l2sc);
257
258         if(newstate == ST_SUBSET)
259         {       /* state function DOES set new state */
260                 NDBGL2(L2_F_MSG, "FSM S-event [%s]: [%s => %s]", l2event_text[event],
261                                            l2state_text[currstate],
262                                            l2state_text[l2sc->Q921_state]);
263         }
264         
265         /* check for illegal new state */
266
267         if(newstate == ST_ILL)
268         {
269                 newstate = currstate;
270                 NDBGL2(L2_F_ERR, "FSM illegal state, state = %s, event = %s!",
271                                 l2state_text[currstate],
272                                 l2event_text[event]);
273         }
274
275         /* check if state machine function has to set new state */
276
277         if(newstate != ST_SUBSET)
278                 l2sc->Q921_state = newstate;        /* no, we set new state */
279
280         if(l2sc->postfsmfunc != NULL)
281         {
282                 NDBGL2(L2_F_MSG, "FSM executing postfsmfunc!");
283                 /* try to avoid an endless loop */
284                 savpostfsmfunc = l2sc->postfsmfunc;
285                 l2sc->postfsmfunc = NULL;
286                 (*savpostfsmfunc)(l2sc->postfsmarg);
287         }
288 }
289
290 #if DO_I4B_DEBUG
291 /*---------------------------------------------------------------------------*
292  *      return pointer to current state description
293  *---------------------------------------------------------------------------*/ 
294 char *i4b_print_l2state(l2_softc_t *l2sc)
295 {
296         return((char *) l2state_text[l2sc->Q921_state]);
297 }
298 #endif
299
300 /*---------------------------------------------------------------------------*
301  *      FSM state ST_TEI_UNAS event dl establish request
302  *---------------------------------------------------------------------------*/ 
303 static void
304 F_TU01(l2_softc_t *l2sc)
305 {
306         NDBGL2(L2_F_MSG, "FSM function F_TU01 executing");
307         i4b_mdl_assign_ind(l2sc);
308 }
309
310 /*---------------------------------------------------------------------------*
311  *      FSM state ST_TEI_UNAS event mdl assign request
312  *---------------------------------------------------------------------------*/ 
313 static void
314 F_TU03(l2_softc_t *l2sc)
315 {
316         NDBGL2(L2_F_MSG, "FSM function F_TU03 executing");
317 }
318
319 /*---------------------------------------------------------------------------*
320  *      FSM state ST_ASG_AW_TEI event mdl assign request
321  *---------------------------------------------------------------------------*/ 
322 static void
323 F_TA03(l2_softc_t *l2sc)
324 {
325         NDBGL2(L2_F_MSG, "FSM function F_TA03 executing");
326 }
327
328 /*---------------------------------------------------------------------------*
329  *      FSM state ST_ASG_AW_TEI event mdl error response
330  *---------------------------------------------------------------------------*/ 
331 static void
332 F_TA04(l2_softc_t *l2sc)
333 {
334         NDBGL2(L2_F_MSG, "FSM function F_TA04 executing");
335 }
336
337 /*---------------------------------------------------------------------------*
338  *      FSM state ST_ASG_AW_TEI event persistent deactivation
339  *---------------------------------------------------------------------------*/ 
340 static void
341 F_TA05(l2_softc_t *l2sc)
342 {
343         NDBGL2(L2_F_MSG, "FSM function F_TA05 executing");
344 }
345
346 /*---------------------------------------------------------------------------*
347  *      FSM state ST_EST_AW_TEI event mdl assign request
348  *---------------------------------------------------------------------------*/ 
349 static void
350 F_TE03(l2_softc_t *l2sc)
351 {
352         NDBGL2(L2_F_MSG, "FSM function F_TE03 executing");
353         i4b_establish_data_link(l2sc);
354         l2sc->l3initiated = 1;
355 }
356
357 /*---------------------------------------------------------------------------*
358  *      FSM state ST_EST_AW_TEI event mdl error response
359  *---------------------------------------------------------------------------*/ 
360 static void
361 F_TE04(l2_softc_t *l2sc)
362 {
363         NDBGL2(L2_F_MSG, "FSM function F_TE04 executing");
364         l2sc->postfsmarg = l2sc->unit;
365         l2sc->postfsmfunc = DL_Rel_Ind_A;
366 }
367
368 /*---------------------------------------------------------------------------*
369  *      FSM state ST_EST_AW_TEI event persistent deactivation
370  *---------------------------------------------------------------------------*/ 
371 static void
372 F_TE05(l2_softc_t *l2sc)
373 {
374         NDBGL2(L2_F_MSG, "FSM function F_TE05 executing");
375         l2sc->postfsmarg = l2sc->unit;
376         l2sc->postfsmfunc = DL_Rel_Ind_A;
377 }
378
379 /*---------------------------------------------------------------------------*
380  *      FSM state ST_TEI_ASGD event dl establish request
381  *---------------------------------------------------------------------------*/ 
382 static void
383 F_T01(l2_softc_t *l2sc)
384 {
385         NDBGL2(L2_F_MSG, "FSM function F_T01 executing");
386         i4b_establish_data_link(l2sc);
387         l2sc->l3initiated = 1;
388 }
389
390 /*---------------------------------------------------------------------------*
391  *      FSM state ST_TEI_ASGD event persistent deactivation
392  *---------------------------------------------------------------------------*/ 
393 static void
394 F_T05(l2_softc_t *l2sc)
395 {
396         NDBGL2(L2_F_MSG, "FSM function F_T05 executing");
397 }
398
399 /*---------------------------------------------------------------------------*
400  *      FSM state ST_TEI_ASGD event mdl remove request
401  *---------------------------------------------------------------------------*/ 
402 static void
403 F_T06(l2_softc_t *l2sc)
404 {
405         NDBGL2(L2_F_MSG, "FSM function F_T06 executing");
406 /*XXX*/ i4b_mdl_assign_ind(l2sc);
407 }
408
409 /*---------------------------------------------------------------------------*
410  *      FSM state ST_TEI_ASGD event rx'd SABME
411  *---------------------------------------------------------------------------*/ 
412 static void
413 F_T07(l2_softc_t *l2sc)
414 {
415         NDBGL2(L2_F_MSG, "FSM function F_T07 executing");
416
417 /* XXX */
418 #ifdef NOTDEF
419         if(NOT able to establish)
420         {
421                 i4b_tx_dm(l2sc, l2sc->rxd_PF);
422                 l2sc->Q921_state = ST_TEI_ASGD;
423                 return;
424         }
425 #endif
426
427         i4b_clear_exception_conditions(l2sc);
428
429         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_ACTIVE);
430         
431         i4b_tx_ua(l2sc, l2sc->rxd_PF);
432
433         l2sc->vs = 0;
434         l2sc->va = 0;
435         l2sc->vr = 0;   
436
437         l2sc->postfsmarg = l2sc->unit;
438         l2sc->postfsmfunc = DL_Est_Ind_A;
439
440         i4b_T203_start(l2sc);   
441
442         l2sc->Q921_state = ST_MULTIFR;
443 }
444
445 /*---------------------------------------------------------------------------*
446  *      FSM state ST_TEI_ASGD event rx'd DISC
447  *---------------------------------------------------------------------------*/ 
448 static void
449 F_T08(l2_softc_t *l2sc)
450 {
451         NDBGL2(L2_F_MSG, "FSM function F_T08 executing");
452         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_IDLE);
453         i4b_tx_ua(l2sc, l2sc->rxd_PF);
454 }
455
456 /*---------------------------------------------------------------------------*
457  *      FSM state ST_TEI_ASGD event rx'd UA
458  *---------------------------------------------------------------------------*/ 
459 static void
460 F_T09(l2_softc_t *l2sc)
461 {
462         NDBGL2(L2_F_MSG, "FSM function F_T09 executing");
463         i4b_mdl_error_ind(l2sc, "F_T09", MDL_ERR_C);
464         i4b_mdl_error_ind(l2sc, "F_T09", MDL_ERR_D);    
465 }
466
467 /*---------------------------------------------------------------------------*
468  *      FSM state ST_TEI_ASGD event rx'd DM
469  *---------------------------------------------------------------------------*/ 
470 static void
471 F_T10(l2_softc_t *l2sc)
472 {
473         NDBGL2(L2_F_MSG, "FSM function F_T10 executing");
474
475         if(l2sc->rxd_PF)
476         {
477                 l2sc->Q921_state = ST_TEI_ASGD;
478         }
479         else
480         {
481 #ifdef NOTDEF
482                 if(NOT able_to_etablish)
483                 {
484                         l2sc->Q921_state = ST_TEI_ASGD;
485                         return;
486                 }
487 #endif
488                 i4b_establish_data_link(l2sc);
489
490                 l2sc->l3initiated = 1;
491
492                 l2sc->Q921_state = ST_AW_EST;
493         }
494 }
495
496 /*---------------------------------------------------------------------------*
497  *      FSM state ST_TEI_ASGD event dl release request
498  *---------------------------------------------------------------------------*/ 
499 static void
500 F_T13(l2_softc_t *l2sc)
501 {
502         NDBGL2(L2_F_MSG, "FSM function F_T13 executing");
503         l2sc->postfsmarg = l2sc->unit;
504         l2sc->postfsmfunc = DL_Rel_Cnf_A;
505 }
506
507 /*---------------------------------------------------------------------------*
508  *      FSM state ST_AW_EST event dl establish request
509  *---------------------------------------------------------------------------*/ 
510 static void
511 F_AE01(l2_softc_t *l2sc)
512 {
513         NDBGL2(L2_F_MSG, "FSM function F_AE01 executing");
514
515         i4b_Dcleanifq(&l2sc->i_queue);
516         
517         l2sc->l3initiated = 1;
518 }
519
520 /*---------------------------------------------------------------------------*
521  *      FSM state ST_AW_EST event persistent deactivation
522  *---------------------------------------------------------------------------*/ 
523 static void
524 F_AE05(l2_softc_t *l2sc)
525 {
526         NDBGL2(L2_F_MSG, "FSM function F_AE05 executing");
527
528         i4b_Dcleanifq(&l2sc->i_queue);  
529
530         l2sc->postfsmarg = l2sc->unit;
531         l2sc->postfsmfunc = DL_Rel_Ind_A;
532
533         i4b_T200_stop(l2sc);
534 }
535
536 /*---------------------------------------------------------------------------*
537  *      FSM state ST_AW_EST event mdl remove request
538  *---------------------------------------------------------------------------*/ 
539 static void
540 F_AE06(l2_softc_t *l2sc)
541 {
542         NDBGL2(L2_F_MSG, "FSM function F_AE06 executing");
543
544         i4b_Dcleanifq(&l2sc->i_queue);  
545
546         l2sc->postfsmarg = l2sc->unit;
547         l2sc->postfsmfunc = DL_Rel_Ind_A;
548
549         i4b_T200_stop(l2sc);
550
551 /*XXX*/ i4b_mdl_assign_ind(l2sc);
552 }
553
554 /*---------------------------------------------------------------------------*
555  *      FSM state ST_AW_EST event rx'd SABME
556  *---------------------------------------------------------------------------*/ 
557 static void
558 F_AE07(l2_softc_t *l2sc)
559 {
560         NDBGL2(L2_F_MSG, "FSM function F_AE07 executing");
561         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_ACTIVE);
562         i4b_tx_ua(l2sc, l2sc->rxd_PF);
563 }
564
565 /*---------------------------------------------------------------------------*
566  *      FSM state ST_AW_EST event rx'd DISC
567  *---------------------------------------------------------------------------*/ 
568 static void
569 F_AE08(l2_softc_t *l2sc)
570 {
571         NDBGL2(L2_F_MSG, "FSM function F_AE08 executing");
572         i4b_tx_dm(l2sc, l2sc->rxd_PF);
573 }
574
575 /*---------------------------------------------------------------------------*
576  *      FSM state ST_AW_EST event rx'd UA
577  *---------------------------------------------------------------------------*/ 
578 static void
579 F_AE09(l2_softc_t *l2sc)
580 {
581         NDBGL2(L2_F_MSG, "FSM function F_AE09 executing");
582
583         if(l2sc->rxd_PF == 0)
584         {
585                 i4b_mdl_error_ind(l2sc, "F_AE09", MDL_ERR_D);
586                 l2sc->Q921_state = ST_AW_EST;
587         }
588         else
589         {
590                 if(l2sc->l3initiated)
591                 {
592                         l2sc->l3initiated = 0;
593                         l2sc->vr = 0;
594                         l2sc->postfsmarg = l2sc->unit;
595                         l2sc->postfsmfunc = DL_Est_Cnf_A;
596                 }
597                 else
598                 {
599                         if(l2sc->vs != l2sc->va)
600                         {
601                                 i4b_Dcleanifq(&l2sc->i_queue);
602                                 l2sc->postfsmarg = l2sc->unit;
603                                 l2sc->postfsmfunc = DL_Est_Ind_A;
604                         }
605                 }
606
607                 MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_ACTIVE);
608                 
609                 i4b_T200_stop(l2sc);
610                 i4b_T203_start(l2sc);
611
612                 l2sc->vs = 0;
613                 l2sc->va = 0;
614
615                 l2sc->Q921_state = ST_MULTIFR;
616         }
617 }
618
619 /*---------------------------------------------------------------------------*
620  *      FSM state ST_AW_EST event rx'd DM
621  *---------------------------------------------------------------------------*/ 
622 static void
623 F_AE10(l2_softc_t *l2sc)
624 {
625         NDBGL2(L2_F_MSG, "FSM function F_AE10 executing");
626
627         if(l2sc->rxd_PF == 0)
628         {
629                 l2sc->Q921_state = ST_AW_EST;
630         }
631         else
632         {
633                 i4b_Dcleanifq(&l2sc->i_queue);
634
635                 l2sc->postfsmarg = l2sc->unit;
636                 l2sc->postfsmfunc = DL_Rel_Ind_A;
637
638                 i4b_T200_stop(l2sc);
639
640                 l2sc->Q921_state = ST_TEI_ASGD;         
641         }
642 }
643
644 /*---------------------------------------------------------------------------*
645  *      FSM state ST_AW_EST event T200 expiry
646  *---------------------------------------------------------------------------*/ 
647 static void
648 F_AE11(l2_softc_t *l2sc)
649 {
650         NDBGL2(L2_F_MSG, "FSM function F_AE11 executing");
651
652         if(l2sc->RC >= N200)
653         {
654                 i4b_Dcleanifq(&l2sc->i_queue);
655
656                 i4b_mdl_error_ind(l2sc, "F_AE11", MDL_ERR_G);
657
658                 l2sc->postfsmarg = l2sc->unit;
659                 l2sc->postfsmfunc = DL_Rel_Ind_A;
660
661                 l2sc->Q921_state = ST_TEI_ASGD;
662         }
663         else
664         {
665                 l2sc->RC++;
666
667                 i4b_tx_sabme(l2sc, P1);
668
669                 i4b_T200_start(l2sc);
670
671                 l2sc->Q921_state = ST_AW_EST;
672         }
673 }
674
675 /*---------------------------------------------------------------------------*
676  *      FSM state ST_AW_EST event dl data request
677  *---------------------------------------------------------------------------*/ 
678 static void
679 F_AE12(l2_softc_t *l2sc)
680 {
681         NDBGL2(L2_F_MSG, "FSM function F_AE12 executing");
682
683         if(l2sc->l3initiated == 0)
684         {
685                 i4b_i_frame_queued_up(l2sc);
686         }
687 }
688
689 /*---------------------------------------------------------------------------*
690  *      FSM state ST_AW_REL event persistent deactivation
691  *---------------------------------------------------------------------------*/ 
692 static void
693 F_AR05(l2_softc_t *l2sc)
694 {
695         NDBGL2(L2_F_MSG, "FSM function F_AR05 executing");
696
697         l2sc->postfsmarg = l2sc->unit;
698         l2sc->postfsmfunc = DL_Rel_Cnf_A;
699
700         i4b_T200_stop(l2sc);
701 }
702
703 /*---------------------------------------------------------------------------*
704  *      FSM state ST_AW_REL event mdl remove request
705  *---------------------------------------------------------------------------*/ 
706 static void
707 F_AR06(l2_softc_t *l2sc)
708 {
709         NDBGL2(L2_F_MSG, "FSM function F_AR06 executing");
710
711         l2sc->postfsmarg = l2sc->unit;
712         l2sc->postfsmfunc = DL_Rel_Cnf_A;
713
714         i4b_T200_stop(l2sc);
715
716 /*XXX*/ i4b_mdl_assign_ind(l2sc);       
717 }
718
719 /*---------------------------------------------------------------------------*
720  *      FSM state ST_AW_REL event rx'd SABME
721  *---------------------------------------------------------------------------*/ 
722 static void
723 F_AR07(l2_softc_t *l2sc)
724 {
725         NDBGL2(L2_F_MSG, "FSM function F_AR07 executing");      
726         i4b_tx_dm(l2sc, l2sc->rxd_PF);
727 }
728
729 /*---------------------------------------------------------------------------*
730  *      FSM state ST_AW_REL event rx'd DISC
731  *---------------------------------------------------------------------------*/ 
732 static void
733 F_AR08(l2_softc_t *l2sc)
734 {
735         NDBGL2(L2_F_MSG, "FSM function F_AR08 executing");
736         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_IDLE);
737         i4b_tx_ua(l2sc, l2sc->rxd_PF);  
738 }
739
740 /*---------------------------------------------------------------------------*
741  *      FSM state ST_AW_REL event rx'd UA
742  *---------------------------------------------------------------------------*/ 
743 static void
744 F_AR09(l2_softc_t *l2sc)
745 {
746         NDBGL2(L2_F_MSG, "FSM function F_AR09 executing");
747
748         if(l2sc->rxd_PF)
749         {
750                 l2sc->postfsmarg = l2sc->unit;
751                 l2sc->postfsmfunc = DL_Rel_Cnf_A;
752
753                 i4b_T200_stop(l2sc);
754
755                 l2sc->Q921_state = ST_TEI_ASGD;
756         }
757         else
758         {
759                 i4b_mdl_error_ind(l2sc, "F_AR09", MDL_ERR_D);
760                 
761                 l2sc->Q921_state = ST_AW_REL;
762         }
763 }
764
765 /*---------------------------------------------------------------------------*
766  *      FSM state ST_AW_REL event rx'd DM
767  *---------------------------------------------------------------------------*/ 
768 static void
769 F_AR10(l2_softc_t *l2sc)
770 {
771         NDBGL2(L2_F_MSG, "FSM function F_AR10 executing");
772
773         if(l2sc->rxd_PF)
774         {
775                 l2sc->postfsmarg = l2sc->unit;
776                 l2sc->postfsmfunc = DL_Rel_Cnf_A;
777
778                 i4b_T200_stop(l2sc);
779
780                 l2sc->Q921_state = ST_TEI_ASGD;
781         }
782         else
783         {
784                 l2sc->Q921_state = ST_AW_REL;
785         }
786 }
787
788 /*---------------------------------------------------------------------------*
789  *      FSM state ST_AW_REL event T200 expiry
790  *---------------------------------------------------------------------------*/ 
791 static void
792 F_AR11(l2_softc_t *l2sc)
793 {
794         NDBGL2(L2_F_MSG, "FSM function F_AR11 executing");
795
796         if(l2sc->RC >= N200)
797         {
798                 i4b_mdl_error_ind(l2sc, "F_AR11", MDL_ERR_H);
799
800                 l2sc->postfsmarg = l2sc->unit;
801                 l2sc->postfsmfunc = DL_Rel_Cnf_A;
802
803                 l2sc->Q921_state = ST_TEI_ASGD;
804         }
805         else
806         {
807                 l2sc->RC++;
808
809                 i4b_tx_disc(l2sc, P1);
810
811                 i4b_T200_start(l2sc);
812
813                 l2sc->Q921_state = ST_AW_REL;
814         }
815 }
816
817 /*---------------------------------------------------------------------------*
818  *      FSM state ST_MULTIFR event dl establish request
819  *---------------------------------------------------------------------------*/ 
820 static void
821 F_MF01(l2_softc_t *l2sc)
822 {
823         NDBGL2(L2_F_MSG, "FSM function F_MF01 executing");
824
825         i4b_Dcleanifq(&l2sc->i_queue);
826
827         i4b_establish_data_link(l2sc);
828         
829         l2sc->l3initiated = 1;
830 }
831
832 /*---------------------------------------------------------------------------*
833  *      FSM state ST_MULTIFR event persistent deactivation
834  *---------------------------------------------------------------------------*/ 
835 static void
836 F_MF05(l2_softc_t *l2sc)
837 {
838         NDBGL2(L2_F_MSG, "FSM function F_MF05 executing");
839
840         i4b_Dcleanifq(&l2sc->i_queue);
841         
842         l2sc->postfsmarg = l2sc->unit;
843         l2sc->postfsmfunc = DL_Rel_Ind_A;
844         
845         i4b_T200_stop(l2sc);
846         i4b_T203_stop(l2sc);
847 }
848
849 /*---------------------------------------------------------------------------*
850  *      FSM state ST_MULTIFR event mdl remove request
851  *---------------------------------------------------------------------------*/ 
852 static void
853 F_MF06(l2_softc_t *l2sc)
854 {
855         NDBGL2(L2_F_MSG, "FSM function F_MF06 executing");
856
857         i4b_Dcleanifq(&l2sc->i_queue);
858         
859         l2sc->postfsmarg = l2sc->unit;
860         l2sc->postfsmfunc = DL_Rel_Ind_A;
861         
862         i4b_T200_stop(l2sc);
863         i4b_T203_stop(l2sc);
864
865 /*XXX*/ i4b_mdl_assign_ind(l2sc);       
866 }
867
868 /*---------------------------------------------------------------------------*
869  *      FSM state ST_MULTIFR event rx'd SABME
870  *---------------------------------------------------------------------------*/ 
871 static void
872 F_MF07(l2_softc_t *l2sc)
873 {
874         NDBGL2(L2_F_MSG, "FSM function F_MF07 executing");
875
876         i4b_clear_exception_conditions(l2sc);
877
878         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_ACTIVE);   
879
880         i4b_tx_ua(l2sc, l2sc->rxd_PF);
881
882         i4b_mdl_error_ind(l2sc, "F_MF07", MDL_ERR_F);
883
884         if(l2sc->vs != l2sc->va)
885         {
886                 i4b_Dcleanifq(&l2sc->i_queue);
887         
888                 l2sc->postfsmarg = l2sc->unit;
889                 l2sc->postfsmfunc = DL_Est_Ind_A;
890         }
891
892         i4b_T200_stop(l2sc);
893         i4b_T203_start(l2sc);
894
895         l2sc->vs = 0;
896         l2sc->va = 0;
897         l2sc->vr = 0;   
898 }
899
900 /*---------------------------------------------------------------------------*
901  *      FSM state ST_MULTIFR event rx'd DISC
902  *---------------------------------------------------------------------------*/ 
903 static void
904 F_MF08(l2_softc_t *l2sc)
905 {
906         NDBGL2(L2_F_MSG, "FSM function F_MF08 executing");
907
908         i4b_Dcleanifq(&l2sc->i_queue);
909         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_IDLE);
910         i4b_tx_ua(l2sc, l2sc->rxd_PF);
911         
912         l2sc->postfsmarg = l2sc->unit;
913         l2sc->postfsmfunc = DL_Rel_Ind_A;
914
915         i4b_T200_stop(l2sc);
916         i4b_T203_stop(l2sc);
917 }
918
919 /*---------------------------------------------------------------------------*
920  *      FSM state ST_MULTIFR event rx'd UA
921  *---------------------------------------------------------------------------*/ 
922 static void
923 F_MF09(l2_softc_t *l2sc)
924 {
925         NDBGL2(L2_F_MSG, "FSM function F_MF09 executing");
926         if(l2sc->rxd_PF)
927                 i4b_mdl_error_ind(l2sc, "F_MF09", MDL_ERR_C);
928         else
929                 i4b_mdl_error_ind(l2sc, "F_MF09", MDL_ERR_D);
930 }
931
932 /*---------------------------------------------------------------------------*
933  *      FSM state ST_MULTIFR event rx'd DM
934  *---------------------------------------------------------------------------*/ 
935 static void
936 F_MF10(l2_softc_t *l2sc)
937 {
938         NDBGL2(L2_F_MSG, "FSM function F_MF10 executing");
939
940         if(l2sc->rxd_PF)
941         {
942                 i4b_mdl_error_ind(l2sc, "F_MF10", MDL_ERR_B);
943                 
944                 l2sc->Q921_state = ST_MULTIFR;
945         }
946         else
947         {
948                 i4b_mdl_error_ind(l2sc, "F_MF10", MDL_ERR_E);
949                 
950                 i4b_establish_data_link(l2sc);
951
952                 l2sc->l3initiated = 0;
953                 
954                 l2sc->Q921_state = ST_AW_EST;
955         }
956 }
957
958 /*---------------------------------------------------------------------------*
959  *      FSM state ST_MULTIFR event T200 expiry
960  *---------------------------------------------------------------------------*/ 
961 static void
962 F_MF11(l2_softc_t *l2sc)
963 {
964         NDBGL2(L2_F_MSG, "FSM function F_MF11 executing");
965
966         l2sc->RC = 0;
967
968         i4b_transmit_enquire(l2sc);
969
970         l2sc->RC++;
971 }
972
973 /*---------------------------------------------------------------------------*
974  *      FSM state ST_MULTIFR event dl data request
975  *---------------------------------------------------------------------------*/ 
976 static void
977 F_MF12(l2_softc_t *l2sc)
978 {
979         NDBGL2(L2_F_MSG, "FSM function F_MF12 executing");
980
981         i4b_i_frame_queued_up(l2sc);
982 }
983
984 /*---------------------------------------------------------------------------*
985  *      FSM state ST_MULTIFR event dl release request
986  *---------------------------------------------------------------------------*/ 
987 static void
988 F_MF13(l2_softc_t *l2sc)
989 {
990         NDBGL2(L2_F_MSG, "FSM function F_MF13 executing");
991
992         i4b_Dcleanifq(&l2sc->i_queue);
993
994         l2sc->RC = 0;
995
996         i4b_tx_disc(l2sc, P1);
997         
998         i4b_T203_stop(l2sc);
999         i4b_T200_restart(l2sc); 
1000 }
1001
1002 /*---------------------------------------------------------------------------*
1003  *      FSM state ST_MULTIFR event T203 expiry
1004  *---------------------------------------------------------------------------*/ 
1005 static void
1006 F_MF14(l2_softc_t *l2sc)
1007 {
1008         NDBGL2(L2_F_MSG, "FSM function F_MF14 executing");
1009
1010         i4b_transmit_enquire(l2sc);
1011
1012         l2sc->RC = 0;
1013 }
1014
1015 /*---------------------------------------------------------------------------*
1016  *      FSM state ST_MULTIFR event set own rx busy
1017  *---------------------------------------------------------------------------*/ 
1018 static void
1019 F_MF15(l2_softc_t *l2sc)
1020 {
1021         NDBGL2(L2_F_MSG, "FSM function F_MF15 executing");
1022
1023         if(l2sc->own_busy == 0)
1024         {
1025                 l2sc->own_busy = 1;
1026
1027                 i4b_tx_rnr_response(l2sc, F0); /* wrong in Q.921 03/93 p 64 */
1028
1029                 l2sc->ack_pend = 0;
1030         }
1031 }
1032
1033 /*---------------------------------------------------------------------------*
1034  *      FSM state ST_MULTIFR event clear own rx busy
1035  *---------------------------------------------------------------------------*/ 
1036 static void
1037 F_MF16(l2_softc_t *l2sc)
1038 {
1039         NDBGL2(L2_F_MSG, "FSM function F_MF16 executing");
1040
1041         if(l2sc->own_busy != 0)
1042         {
1043                 l2sc->own_busy = 0;
1044
1045                 i4b_tx_rr_response(l2sc, F0); /* wrong in Q.921 03/93 p 64 */
1046
1047                 l2sc->ack_pend = 0;
1048         }
1049 }
1050
1051 /*---------------------------------------------------------------------------*
1052  *      FSM state ST_MULTIFR event rx'd RR
1053  *---------------------------------------------------------------------------*/ 
1054 static void
1055 F_MF17(l2_softc_t *l2sc)
1056 {
1057         NDBGL2(L2_F_MSG, "FSM function F_MF17 executing");
1058
1059         l2sc->peer_busy = 0;
1060
1061         if(l2sc->rxd_CR == CR_CMD_FROM_NT)
1062         {
1063                 if(l2sc->rxd_PF == 1)
1064                 {
1065                         i4b_enquiry_response(l2sc);
1066                 }
1067         }
1068         else
1069         {
1070                 if(l2sc->rxd_PF == 1)
1071                 {
1072                         i4b_mdl_error_ind(l2sc, "F_MF17", MDL_ERR_A);
1073                 }
1074         }
1075
1076         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1077         {
1078                 if(l2sc->rxd_NR == l2sc->vs)
1079                 {
1080                         l2sc->va = l2sc->rxd_NR;
1081                         i4b_T200_stop(l2sc);
1082                         i4b_T203_restart(l2sc);
1083                 }
1084                 else if(l2sc->rxd_NR != l2sc->va)
1085                 {
1086                         l2sc->va = l2sc->rxd_NR;
1087                         i4b_T200_restart(l2sc);
1088                 }
1089                 l2sc->Q921_state = ST_MULTIFR;
1090         }
1091         else
1092         {
1093                 i4b_nr_error_recovery(l2sc);
1094                 l2sc->Q921_state = ST_AW_EST;
1095         }
1096 }
1097
1098 /*---------------------------------------------------------------------------*
1099  *      FSM state ST_MULTIFR event rx'd REJ
1100  *---------------------------------------------------------------------------*/ 
1101 static void
1102 F_MF18(l2_softc_t *l2sc)
1103 {
1104         NDBGL2(L2_F_MSG, "FSM function F_MF18 executing");
1105
1106         l2sc->peer_busy = 0;
1107
1108         if(l2sc->rxd_CR == CR_CMD_FROM_NT)
1109         {
1110                 if(l2sc->rxd_PF == 1)
1111                 {
1112                         i4b_enquiry_response(l2sc);
1113                 }
1114         }
1115         else
1116         {
1117                 if(l2sc->rxd_PF == 1)
1118                 {
1119                         i4b_mdl_error_ind(l2sc, "F_MF18", MDL_ERR_A);
1120                 }
1121         }
1122
1123         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1124         {
1125                 l2sc->va = l2sc->rxd_NR;
1126                 i4b_T200_stop(l2sc);
1127                 i4b_T203_start(l2sc);
1128                 i4b_invoke_retransmission(l2sc, l2sc->rxd_NR);
1129                 l2sc->Q921_state = ST_MULTIFR;
1130         }
1131         else
1132         {
1133                 i4b_nr_error_recovery(l2sc);
1134                 l2sc->Q921_state = ST_AW_EST;           
1135         }
1136 }
1137
1138 /*---------------------------------------------------------------------------*
1139  *      FSM state ST_MULTIFR event rx'd RNR
1140  *---------------------------------------------------------------------------*/ 
1141 static void
1142 F_MF19(l2_softc_t *l2sc)
1143 {
1144         NDBGL2(L2_F_MSG, "FSM function F_MF19 executing");
1145
1146         l2sc->peer_busy = 1;
1147
1148         if(l2sc->rxd_CR == CR_CMD_FROM_NT)
1149         {
1150                 if(l2sc->rxd_PF == 1)
1151                 {
1152                         i4b_enquiry_response(l2sc);
1153                 }
1154         }
1155         else
1156         {
1157                 if(l2sc->rxd_PF == 1)
1158                 {
1159                         i4b_mdl_error_ind(l2sc, "F_MF19", MDL_ERR_A);
1160                 }
1161         }
1162
1163         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1164         {
1165                 l2sc->va = l2sc->rxd_NR;
1166                 i4b_T203_stop(l2sc);
1167                 i4b_T200_restart(l2sc);
1168                 l2sc->Q921_state = ST_MULTIFR;
1169         }
1170         else
1171         {
1172                 i4b_nr_error_recovery(l2sc);
1173                 l2sc->Q921_state = ST_AW_EST;                
1174         }
1175 }
1176
1177 /*---------------------------------------------------------------------------*
1178  *      FSM state ST_MULTIFR event rx'd FRMR
1179  *---------------------------------------------------------------------------*/ 
1180 static void
1181 F_MF20(l2_softc_t *l2sc)
1182 {
1183         NDBGL2(L2_F_MSG, "FSM function F_MF20 executing");
1184
1185         i4b_mdl_error_ind(l2sc, "F_MF20", MDL_ERR_K);
1186
1187         i4b_establish_data_link(l2sc);
1188
1189         l2sc->l3initiated = 0;
1190 }
1191
1192 /*---------------------------------------------------------------------------*
1193  *      FSM state ST_TIMREC event dl establish request
1194  *---------------------------------------------------------------------------*/ 
1195 static void
1196 F_TR01(l2_softc_t *l2sc)
1197 {
1198         NDBGL2(L2_F_MSG, "FSM function F_TR01 executing");
1199
1200         i4b_Dcleanifq(&l2sc->i_queue);
1201
1202         i4b_establish_data_link(l2sc);
1203
1204         l2sc->l3initiated = 1;
1205 }
1206
1207 /*---------------------------------------------------------------------------*
1208  *      FSM state ST_TIMREC event persistent deactivation
1209  *---------------------------------------------------------------------------*/ 
1210 static void
1211 F_TR05(l2_softc_t *l2sc)
1212 {
1213         NDBGL2(L2_F_MSG, "FSM function F_TR05 executing");
1214
1215         i4b_Dcleanifq(&l2sc->i_queue);  
1216
1217         l2sc->postfsmarg = l2sc->unit;
1218         l2sc->postfsmfunc = DL_Rel_Ind_A;
1219
1220         i4b_T200_stop(l2sc);
1221 }
1222
1223 /*---------------------------------------------------------------------------*
1224  *      FSM state ST_TIMREC event mdl remove request
1225  *---------------------------------------------------------------------------*/ 
1226 static void
1227 F_TR06(l2_softc_t *l2sc)
1228 {
1229         NDBGL2(L2_F_MSG, "FSM function F_TR06 executing");
1230
1231         i4b_Dcleanifq(&l2sc->i_queue);
1232
1233         l2sc->postfsmarg = l2sc->unit;
1234         l2sc->postfsmfunc = DL_Rel_Ind_A;
1235
1236         i4b_T200_stop(l2sc);
1237
1238 /*XXX*/ i4b_mdl_assign_ind(l2sc);       
1239 }
1240
1241 /*---------------------------------------------------------------------------*
1242  *      FSM state ST_TIMREC event rx'd SABME
1243  *---------------------------------------------------------------------------*/ 
1244 static void
1245 F_TR07(l2_softc_t *l2sc)
1246 {
1247         NDBGL2(L2_F_MSG, "FSM function F_TR07 executing");
1248
1249         i4b_clear_exception_conditions(l2sc);
1250
1251         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_ACTIVE);
1252         
1253         i4b_tx_ua(l2sc, l2sc->rxd_PF);
1254
1255         i4b_mdl_error_ind(l2sc, "F_TR07", MDL_ERR_F);
1256
1257         if(l2sc->vs != l2sc->va)
1258         {
1259                 i4b_Dcleanifq(&l2sc->i_queue);          
1260
1261                 l2sc->postfsmarg = l2sc->unit;
1262                 l2sc->postfsmfunc = DL_Est_Ind_A;
1263         }
1264
1265         i4b_T200_stop(l2sc);
1266         i4b_T203_start(l2sc);
1267         
1268         l2sc->vs = 0;
1269         l2sc->va = 0;
1270         l2sc->vr = 0;
1271 }
1272
1273 /*---------------------------------------------------------------------------*
1274  *      FSM state ST_TIMREC event rx'd DISC
1275  *---------------------------------------------------------------------------*/ 
1276 static void
1277 F_TR08(l2_softc_t *l2sc)
1278 {
1279         NDBGL2(L2_F_MSG, "FSM function F_TR08 executing");
1280
1281         i4b_Dcleanifq(&l2sc->i_queue);          
1282         MDL_Status_Ind(l2sc->unit, STI_L2STAT, LAYER_IDLE);
1283         i4b_tx_ua(l2sc, l2sc->rxd_PF);
1284
1285         l2sc->postfsmarg = l2sc->unit;
1286         l2sc->postfsmfunc = DL_Rel_Ind_A;
1287
1288         i4b_T200_stop(l2sc);
1289 }
1290
1291 /*---------------------------------------------------------------------------*
1292  *      FSM state ST_TIMREC event rx'd UA
1293  *---------------------------------------------------------------------------*/ 
1294 static void
1295 F_TR09(l2_softc_t *l2sc)
1296 {
1297         NDBGL2(L2_F_MSG, "FSM function F_TR09 executing");
1298         if(l2sc->rxd_PF)
1299                 i4b_mdl_error_ind(l2sc, "F_TR09", MDL_ERR_C);
1300         else
1301                 i4b_mdl_error_ind(l2sc, "F_TR09", MDL_ERR_D);   
1302 }
1303
1304 /*---------------------------------------------------------------------------*
1305  *      FSM state ST_TIMREC event rx'd DM
1306  *---------------------------------------------------------------------------*/ 
1307 static void
1308 F_TR10(l2_softc_t *l2sc)
1309 {
1310         NDBGL2(L2_F_MSG, "FSM function F_TR10 executing");
1311
1312         if(l2sc->rxd_PF)
1313         {
1314                 i4b_mdl_error_ind(l2sc, "F_TR10", MDL_ERR_B);
1315         }
1316         else
1317         {
1318                 i4b_mdl_error_ind(l2sc, "F_TR10", MDL_ERR_E);
1319         }
1320
1321         i4b_establish_data_link(l2sc);
1322
1323         l2sc->l3initiated = 0;
1324 }
1325
1326 /*---------------------------------------------------------------------------*
1327  *      FSM state ST_TIMREC event T200 expiry
1328  *---------------------------------------------------------------------------*/ 
1329 static void
1330 F_TR11(l2_softc_t *l2sc)
1331 {
1332         NDBGL2(L2_F_MSG, "FSM function F_TR11 executing");
1333
1334         if(l2sc->RC >= N200)
1335         {
1336                 i4b_mdl_error_ind(l2sc, "F_TR11", MDL_ERR_I);
1337
1338                 i4b_establish_data_link(l2sc);
1339
1340                 l2sc->l3initiated = 0;
1341
1342                 l2sc->Q921_state = ST_AW_EST;
1343         }
1344         else
1345         {
1346                 i4b_transmit_enquire(l2sc);
1347
1348                 l2sc->RC++;
1349
1350                 l2sc->Q921_state = ST_TIMREC;
1351         }
1352 }
1353
1354 /*---------------------------------------------------------------------------*
1355  *      FSM state ST_TIMREC event dl data request
1356  *---------------------------------------------------------------------------*/ 
1357 static void
1358 F_TR12(l2_softc_t *l2sc)
1359 {
1360         NDBGL2(L2_F_MSG, "FSM function F_TR12 executing");
1361
1362         i4b_i_frame_queued_up(l2sc);
1363 }
1364
1365 /*---------------------------------------------------------------------------*
1366  *      FSM state ST_TIMREC event dl release request
1367  *---------------------------------------------------------------------------*/ 
1368 static void
1369 F_TR13(l2_softc_t *l2sc)
1370 {
1371         NDBGL2(L2_F_MSG, "FSM function F_TR13 executing");
1372
1373         i4b_Dcleanifq(&l2sc->i_queue);                  
1374
1375         l2sc->RC = 0;
1376
1377         i4b_tx_disc(l2sc, P1);
1378
1379         i4b_T200_restart(l2sc);
1380 }
1381
1382 /*---------------------------------------------------------------------------*
1383  *      FSM state ST_TIMREC event set own rx busy
1384  *---------------------------------------------------------------------------*/ 
1385 static void
1386 F_TR15(l2_softc_t *l2sc)
1387 {
1388         NDBGL2(L2_F_MSG, "FSM function F_TR15 executing");
1389
1390         if(l2sc->own_busy == 0)
1391         {
1392                 l2sc->own_busy = 1;
1393
1394                 i4b_tx_rnr_response(l2sc, F0);
1395
1396                 l2sc->ack_pend = 0;
1397         }
1398 }
1399
1400 /*---------------------------------------------------------------------------*
1401  *      FSM state ST_TIMREC event clear own rx busy
1402  *---------------------------------------------------------------------------*/ 
1403 static void
1404 F_TR16(l2_softc_t *l2sc)
1405 {
1406         NDBGL2(L2_F_MSG, "FSM function F_TR16 executing");
1407
1408         if(l2sc->own_busy != 0)
1409         {
1410                 l2sc->own_busy = 0;
1411
1412                 i4b_tx_rr_response(l2sc, F0);   /* this is wrong         */
1413                                                 /* in Q.921 03/93 p 74 ! */
1414                 l2sc->ack_pend = 0;
1415         }
1416 }
1417
1418 /*---------------------------------------------------------------------------*
1419  *      FSM state ST_TIMREC event rx'd RR
1420  *---------------------------------------------------------------------------*/ 
1421 static void
1422 F_TR17(l2_softc_t *l2sc)
1423 {
1424         NDBGL2(L2_F_MSG, "FSM function F_TR17 executing");
1425
1426         l2sc->peer_busy = 0;
1427
1428         if(l2sc->rxd_CR == CR_CMD_FROM_NT)
1429         {
1430                 if(l2sc->rxd_PF == 1)
1431                 {
1432                         i4b_enquiry_response(l2sc);
1433                 }
1434         }
1435         else
1436         {
1437                 if(l2sc->rxd_PF == 1)
1438                 {
1439                         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1440                         {
1441                                 l2sc->va = l2sc->rxd_NR;
1442                                 i4b_T200_stop(l2sc);
1443                                 i4b_T203_start(l2sc);
1444                                 i4b_invoke_retransmission(l2sc, l2sc->rxd_NR);
1445                                 l2sc->Q921_state = ST_MULTIFR;
1446                                 return;
1447                         }
1448                         else
1449                         {
1450                                 i4b_nr_error_recovery(l2sc);
1451                                 l2sc->Q921_state = ST_AW_EST;
1452                                 return;
1453                         }
1454                 }
1455         }
1456
1457         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1458         {
1459                 l2sc->va = l2sc->rxd_NR;
1460                 l2sc->Q921_state = ST_TIMREC;
1461         }
1462         else
1463         {
1464                 i4b_nr_error_recovery(l2sc);
1465                 l2sc->Q921_state = ST_AW_EST;
1466         }
1467 }
1468
1469 /*---------------------------------------------------------------------------*
1470  *      FSM state ST_TIMREC event 
1471  *---------------------------------------------------------------------------*/ 
1472 static void
1473 F_TR18(l2_softc_t *l2sc)
1474 {
1475         NDBGL2(L2_F_MSG, "FSM function F_TR18 executing");
1476
1477         l2sc->peer_busy = 0;
1478
1479         if(l2sc->rxd_CR == CR_CMD_FROM_NT)
1480         {
1481                 if(l2sc->rxd_PF == 1)
1482                 {
1483                         i4b_enquiry_response(l2sc);
1484                 }
1485         }
1486         else
1487         {
1488                 if(l2sc->rxd_PF == 1)
1489                 {
1490                         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1491                         {
1492                                 l2sc->va = l2sc->rxd_NR;
1493                                 i4b_T200_stop(l2sc);
1494                                 i4b_T203_start(l2sc);
1495                                 i4b_invoke_retransmission(l2sc, l2sc->rxd_NR);
1496                                 l2sc->Q921_state = ST_MULTIFR;
1497                                 return;
1498                         }
1499                         else
1500                         {
1501                                 i4b_nr_error_recovery(l2sc);
1502                                 l2sc->Q921_state = ST_AW_EST;
1503                                 return;
1504                         }
1505                 }
1506         }
1507
1508         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1509         {
1510                 l2sc->va = l2sc->rxd_NR;
1511                 l2sc->Q921_state = ST_TIMREC;
1512         }
1513         else
1514         {
1515                 i4b_nr_error_recovery(l2sc);
1516                 l2sc->Q921_state = ST_AW_EST;
1517         }
1518 }
1519
1520 /*---------------------------------------------------------------------------*
1521  *      FSM state ST_TIMREC event rx'd RNR
1522  *---------------------------------------------------------------------------*/ 
1523 static void
1524 F_TR19(l2_softc_t *l2sc)
1525 {
1526         NDBGL2(L2_F_MSG, "FSM function F_TR19 executing");
1527
1528         l2sc->peer_busy = 0;
1529
1530         if(l2sc->rxd_CR == CR_CMD_FROM_NT)
1531         {
1532                 if(l2sc->rxd_PF == 1)
1533                 {
1534                         i4b_enquiry_response(l2sc);
1535                 }
1536         }
1537         else
1538         {
1539                 if(l2sc->rxd_PF == 1)
1540                 {
1541                         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1542                         {
1543                                 l2sc->va = l2sc->rxd_NR;
1544                                 i4b_T200_restart(l2sc);
1545                                 i4b_invoke_retransmission(l2sc, l2sc->rxd_NR);
1546                                 l2sc->Q921_state = ST_MULTIFR;
1547                                 return;
1548                         }
1549                         else
1550                         {
1551                                 i4b_nr_error_recovery(l2sc);
1552                                 l2sc->Q921_state = ST_AW_EST;
1553                                 return;
1554                         }
1555                 }
1556         }
1557
1558         if(i4b_l2_nr_ok(l2sc->rxd_NR, l2sc->va, l2sc->vs))
1559         {
1560                 l2sc->va = l2sc->rxd_NR;
1561                 l2sc->Q921_state = ST_TIMREC;
1562         }
1563         else
1564         {
1565                 i4b_nr_error_recovery(l2sc);
1566                 l2sc->Q921_state = ST_AW_EST;
1567         }
1568 }
1569
1570 /*---------------------------------------------------------------------------*
1571  *      FSM state ST_TIMREC event rx'd FRMR
1572  *---------------------------------------------------------------------------*/ 
1573 static void
1574 F_TR20(l2_softc_t *l2sc)
1575 {
1576         NDBGL2(L2_F_MSG, "FSM function F_TR20 executing");
1577
1578         i4b_mdl_error_ind(l2sc, "F_TR20", MDL_ERR_K);
1579
1580         i4b_establish_data_link(l2sc);
1581
1582         l2sc->l3initiated = 0;
1583 }
1584         
1585 #endif /* NI4BQ921 > 0 */