1 
2 #include "../h/param.h"
3 #include "../h/systm.h"
4 #include "../h/clock.h"
5 #include "../h/mbuf.h"
6 #include "../h/protosw.h"
7 #include "../h/socket.h"
8 #include "../net/dn_systm.h"
9 #include "../net/if.h"
10 #include "../net/tp.h"
11 #include "../net/tp_var.h"
12 
13 
14 /*
15  * Initialize a few of the Transport variables here.
16  */
17 tp_init()
18 {
19 	tp_host = 244;
20 	tprp.tprp_nn = 255;	/* max node number */
21 }
22 
23 /*
24  * Attach a DECnet interface.
25  * For now, since we are an end node,
26  * there can only be one.
27  */
28 tp_attach(ifp)
29 	register struct ifnet *ifp;
30 {
31 	if (tpifp) {
32 		printf("tp: Only one DECnet interface allowed, ");
33 		printf("%s%d ignored\n", ifp->if_name, ifp->if_unit);
34 		return;
35 	}
36 	tpifp = ifp;
37 }
38 
39 /*
40  * Transport input routine.  Decode header, process
41  * initialization messages, flush other control messages,
42  * and strip route headers and pass to NSP.
43  */
44 tp_input()
45 {
46 	register struct mbuf *m;
47 	register char *p;
48 
49 next:
50 	/*
51 	 * Get next packet off input queue.
52 	 */
53 	IF_DEQUEUE(&tpintrq, m);
54 	if (m == 0)
55 		return;
56 	p = mtod(m, char *);
57 	switch (*p & TP_MSGTYPE) {
58 	/*
59 	 * Transport initialization message from neighbor.
60 	 */
61 	case TP_INIT:
62 	{
63 		register struct tpin *t = (struct tpin *)p;
64 
65 		printf("tpinit: node %d, %d, blksize %d, ver %o.%o.%o\n",
66 			D_SHORT(t->tpin_srcnode), t->tpin_tiinfo,
67 			D_SHORT(t->tpin_blksize),
68 			t->tpin_ver[0], t->tpin_ver[1], t->tpin_ver[2]);
69 		/* perform a few consistency checks */
70 		if (m->m_len < sizeof (struct tpin)) {
71 			tpstat.tps_badinit++;
72 			break;
73 		}
74 		if (D_SHORT(t->tpin_srcnode) > tprp.tprp_nn) {
75 			tpstat.tps_badinit++;
76 			break;
77 		}
78 		if (t->tpin_res != 0) {
79 			tpstat.tps_badinit++;
80 			break;
81 		}
82 		tpstat.tps_init++;
83 		if (tpstate == TPS_TIS) {
84 			tpstate = TPS_RUN;
85 			wakeup((caddr_t)&tpstate);
86 		} else if (tpstate == TPS_HALT) {
87 			tp_linit();
88 			tpstate = TPS_RUN;
89 		}
90 		break;
91 	}
92 
93 	/*
94 	 * Route header.  Flush bad ones,
95 	 * strip good ones and pass to NSP.
96 	 */
97 	case TP_RH:
98 	{
99 		register struct tprh *t = (struct tprh *)p;
100 
101 		/*
102 		 * Is it a reasonable route header?
103 		 */
104 		if (tpstate != TPS_RUN) {
105 			printf("tp: not running!\n");
106 			break;
107 		}
108 		if (t->tprh_rtflg & TPRF_EV) {
109 			printf("tp: got P2 ASCII header\n");
110 			tpstat.tps_p2hdr++;
111 			break;
112 		}
113 		if (t->tprh_rtflg & TPRF_RTS) {
114 			printf("tp: got returned packet\n");
115 			tpstat.tps_returned++;
116 			break;
117 		}
118 		if (m->m_len <= sizeof (struct tprh)) {
119 			printf("tp: got short packet, %d\n", m->m_len);
120 			tpstat.tps_shortpacket++;
121 			break;
122 		}
123 		if (D_SHORT(t->tprh_srcnode) > tprp.tprp_nn) {
124 			tpstat.tps_badsrc++;
125 			break;
126 		}
127 
128 		/*
129 		 * Is it for us?  If so,
130 		 * add it to the NSP input queue.
131 		 */
132 		if (D_SHORT(t->tprh_dstnode) != tp_host) {
133 			printf("tp: not for me, %d\n", D_SHORT(t->tprh_dstnode));
134 			tpstat.tps_notforme++;
135 			break;
136 		}
137 		setnspintr();
138 		IF_ENQUEUE(&nspintrq, m);
139 		goto next;
140 	}
141 
142 	/*
143 	 * Verification messge.  We should never see one
144 	 * of these because we never ask for one.  Flush it.
145 	 */
146 	case TP_VERIF:
147 		printf("tp: got verification message\n");
148 		tpstat.tps_verif++;
149 		break;
150 
151 	/*
152 	 * Hello and test message.  Make sure it's
153 	 * valid then flush it.
154 	 */
155 	case TP_TEST:
156 	{
157 		register struct tpht *t = (struct tpht *)p;
158 		register int i;
159 
160 		if (D_SHORT(t->tpht_srcnode) > tprp.tprp_nn) {
161 			tpstat.tps_badsrc++;
162 			break;
163 		}
164 		if ((i = t->tpht_cnt) < 0 || i > 128) {
165 			printf("tp: test, bad count, %d\n", i);
166 			tpstat.tps_badtest++;
167 			break;
168 		}
169 		if (m->m_len != sizeof (struct tpht) + i - 1) {
170 			printf("tp: test, bad len, %d\n", m->m_len);
171 			tpstat.tps_bad_test++;
172 			break;
173 		}
174 		for (p = t->tpht_data; i--; p++)
175 			if (*p != 0252) {
176 				printf("tp: test, bad data, %o\n", *p);
177 				tpstat.tps_badtest++;
178 				break;
179 			}
180 		break;
181 	}
182 
183 	/*
184 	 * Routing message.  We should never get this,
185 	 * at least not yet.  Just flush it.
186 	 */
187 	case TP_ROUTE:
188 		printf("tp: got routing message\n");
189 		tpstat.tps_route++;
190 		break;
191 
192 	default:
193 		printf("tp: unknown packet type, 0x%x\n", *p);
194 		tpstat.tps_unknown++;
195 		break;
196 	}
197 
198 	/*
199 	 * Free the current packet and get the next one.
200 	 */
201 	m_freem(m);
202 	goto next;
203 }
204