141705Ssklower /*
241705Ssklower * Copyright (c) University of British Columbia, 1984
3*63216Sbostic * Copyright (c) 1990, 1993
4*63216Sbostic * The Regents of the University of California. All rights reserved.
541705Ssklower *
641705Ssklower * This code is derived from software contributed to Berkeley by
741705Ssklower * the Laboratory for Computation Vision and the Computer Science Department
841705Ssklower * of the University of British Columbia.
941705Ssklower *
1041705Ssklower * %sccs.include.redist.c%
1141705Ssklower *
12*63216Sbostic * @(#)hd_timer.c 8.1 (Berkeley) 06/10/93
1341705Ssklower */
1441588Ssklower
1556530Sbostic #include <sys/param.h>
1656530Sbostic #include <sys/systm.h>
1756530Sbostic #include <sys/mbuf.h>
1856530Sbostic #include <sys/domain.h>
1956530Sbostic #include <sys/socket.h>
2056530Sbostic #include <sys/protosw.h>
2156530Sbostic #include <sys/errno.h>
2256530Sbostic #include <sys/time.h>
2356530Sbostic #include <sys/kernel.h>
2441588Ssklower
2556530Sbostic #include <net/if.h>
2641588Ssklower
2756530Sbostic #include <netccitt/hdlc.h>
2856530Sbostic #include <netccitt/hd_var.h>
2956530Sbostic #include <netccitt/x25.h>
3041588Ssklower
3141588Ssklower /*
3241588Ssklower * these can be patched with adb if the
3341588Ssklower * default values are inappropriate
3441588Ssklower */
3541588Ssklower
3641588Ssklower int hd_t1 = T1;
3741588Ssklower int hd_t3 = T3;
3841588Ssklower int hd_n2 = N2;
3941588Ssklower
4041588Ssklower /*
4141588Ssklower * HDLC TIMER
4241588Ssklower *
4341588Ssklower * This routine is called every 500ms by the kernel. Decrement timer by this
4441588Ssklower * amount - if expired then process the event.
4541588Ssklower */
4641588Ssklower
hd_timer()4741588Ssklower hd_timer ()
4841588Ssklower {
4941588Ssklower register struct hdcb *hdp;
5041588Ssklower register int s = splimp ();
5141588Ssklower
5241588Ssklower for (hdp = hdcbhead; hdp; hdp = hdp->hd_next) {
5341588Ssklower if (hdp->hd_rrtimer && (--hdp->hd_rrtimer == 0)) {
5441588Ssklower if (hdp->hd_lasttxnr != hdp->hd_vr)
5541588Ssklower hd_writeinternal (hdp, RR, POLLOFF);
5641588Ssklower }
5741588Ssklower
5841588Ssklower if (!(hdp->hd_timer && --hdp->hd_timer == 0))
5941588Ssklower continue;
6041588Ssklower
6141588Ssklower switch (hdp->hd_state) {
6241588Ssklower case INIT:
6341588Ssklower case DISC_SENT:
6441588Ssklower hd_writeinternal (hdp, DISC, POLLON);
6541588Ssklower break;
6641588Ssklower
6741588Ssklower case ABM:
6841588Ssklower if (hdp->hd_lastrxnr != hdp->hd_vs) { /* XXX */
6941588Ssklower hdp->hd_timeouts++;
7041588Ssklower hd_resend_iframe (hdp);
7141588Ssklower }
7241588Ssklower break;
7341588Ssklower
7441588Ssklower case WAIT_SABM:
7541588Ssklower hd_writeinternal (hdp, FRMR, POLLOFF);
7641588Ssklower if (++hdp->hd_retxcnt == hd_n2) {
7741588Ssklower hdp->hd_retxcnt = 0;
7841588Ssklower hd_writeinternal (hdp, SABM, POLLOFF);
7941588Ssklower hdp->hd_state = WAIT_UA;
8041588Ssklower }
8141588Ssklower break;
8241588Ssklower
8341588Ssklower case DM_SENT:
8441588Ssklower if (++hdp->hd_retxcnt == hd_n2) {
8541588Ssklower /* Notify the packet level. */
8649927Ssklower (void) pk_ctlinput (PRC_LINKDOWN, hdp->hd_pkp);
8741588Ssklower hdp->hd_retxcnt = 0;
8841588Ssklower hdp->hd_state = SABM_SENT;
8941588Ssklower hd_writeinternal (hdp, SABM, POLLOFF);
9041588Ssklower } else
9141588Ssklower hd_writeinternal (hdp, DM, POLLOFF);
9241588Ssklower break;
9341588Ssklower
9441588Ssklower case WAIT_UA:
9541588Ssklower if (++hdp->hd_retxcnt == hd_n2) {
9641588Ssklower hdp->hd_retxcnt = 0;
9741588Ssklower hd_writeinternal (hdp, DM, POLLOFF);
9841588Ssklower hdp->hd_state = DM_SENT;
9941588Ssklower } else
10041588Ssklower hd_writeinternal (hdp, SABM, POLLOFF);
10141588Ssklower break;
10241588Ssklower
10341588Ssklower case SABM_SENT:
10441588Ssklower /* Do this indefinitely. */
10541588Ssklower hd_writeinternal (hdp, SABM, POLLON);
10641588Ssklower break;
10741588Ssklower
10841588Ssklower case DISCONNECTED:
10941588Ssklower /*
11041588Ssklower * Poll the interface driver flags waiting
11141588Ssklower * for the IFF_UP bit to come on.
11241588Ssklower */
11341588Ssklower if (hdp->hd_ifp->if_flags & IFF_UP)
11441588Ssklower hdp->hd_state = INIT;
11541588Ssklower
11641588Ssklower }
11741588Ssklower SET_TIMER (hdp);
11841588Ssklower }
11941588Ssklower
12041588Ssklower splx (s);
12141588Ssklower }
122