xref: /freebsd/sys/dev/sbni/if_sbni.c (revision 30d239bc4c510432e65a84fa1c14ed67a3ab1c92)
1 /*-
2  * Copyright (c) 1997-2001 Granch, Ltd. All rights reserved.
3  * Author: Denis I.Timofeev <timofeev@granch.ru>
4  *
5  * Redistributon and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice unmodified, this list of conditions, and the following
10  *    disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23  * LIABILITY, OR TORT (INCLUDING NEIGENCE OR OTHERWISE) ARISING IN ANY WAY
24  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25  * SUCH DAMAGE.
26  *
27  */
28 
29 #include <sys/cdefs.h>
30 __FBSDID("$FreeBSD$");
31 
32 /*
33  * Device driver for Granch SBNI12 leased line adapters
34  *
35  * Revision 2.0.0  1997/08/06
36  * Initial revision by Alexey Zverev
37  *
38  * Revision 2.0.1 1997/08/11
39  * Additional internal statistics support (tx statistics)
40  *
41  * Revision 2.0.2 1997/11/05
42  * if_bpf bug has been fixed
43  *
44  * Revision 2.0.3 1998/12/20
45  * Memory leakage has been eliminated in
46  * the sbni_st and sbni_timeout routines.
47  *
48  * Revision 3.0 2000/08/10 by Yaroslav Polyakov
49  * Support for PCI cards. 4.1 modification.
50  *
51  * Revision 3.1 2000/09/12
52  * Removed extra #defines around bpf functions
53  *
54  * Revision 4.0 2000/11/23 by Denis Timofeev
55  * Completely redesigned the buffer management
56  *
57  * Revision 4.1 2001/01/21
58  * Support for PCI Dual cards and new SBNI12D-10, -11 Dual/ISA cards
59  *
60  * Written with reference to NE2000 driver developed by David Greenman.
61  */
62 
63 
64 #include <sys/param.h>
65 #include <sys/systm.h>
66 #include <sys/socket.h>
67 #include <sys/sockio.h>
68 #include <sys/mbuf.h>
69 #include <sys/kernel.h>
70 #include <sys/priv.h>
71 #include <sys/proc.h>
72 #include <sys/callout.h>
73 #include <sys/syslog.h>
74 #include <sys/random.h>
75 
76 #include <machine/bus.h>
77 #include <sys/rman.h>
78 #include <machine/resource.h>
79 
80 #include <net/if.h>
81 #include <net/if_dl.h>
82 #include <net/ethernet.h>
83 #include <net/bpf.h>
84 #include <net/if_types.h>
85 
86 #include <dev/sbni/if_sbnireg.h>
87 #include <dev/sbni/if_sbnivar.h>
88 
89 #define ASM_CRC 1
90 
91 static void	sbni_init(void *);
92 static void	sbni_start(struct ifnet *);
93 static int	sbni_ioctl(struct ifnet *, u_long, caddr_t);
94 static void	sbni_watchdog(struct ifnet *);
95 static void	sbni_stop(struct sbni_softc *);
96 static void	handle_channel(struct sbni_softc *);
97 
98 static void	card_start(struct sbni_softc *);
99 static int	recv_frame(struct sbni_softc *);
100 static void	send_frame(struct sbni_softc *);
101 static int	upload_data(struct sbni_softc *, u_int, u_int, u_int, u_int32_t);
102 static int	skip_tail(struct sbni_softc *, u_int, u_int32_t);
103 static void	interpret_ack(struct sbni_softc *, u_int);
104 static void	download_data(struct sbni_softc *, u_int32_t *);
105 static void	prepare_to_send(struct sbni_softc *);
106 static void	drop_xmit_queue(struct sbni_softc *);
107 static int	get_rx_buf(struct sbni_softc *);
108 static void	indicate_pkt(struct sbni_softc *);
109 static void	change_level(struct sbni_softc *);
110 static int	check_fhdr(struct sbni_softc *, u_int *, u_int *,
111 			   u_int *, u_int *, u_int32_t *);
112 static int	append_frame_to_pkt(struct sbni_softc *, u_int, u_int32_t);
113 static void	timeout_change_level(struct sbni_softc *);
114 static void	send_frame_header(struct sbni_softc *, u_int32_t *);
115 static void	set_initial_values(struct sbni_softc *, struct sbni_flags);
116 
117 static u_int32_t	calc_crc32(u_int32_t, caddr_t, u_int);
118 static timeout_t	sbni_timeout;
119 
120 static __inline u_char	sbni_inb(struct sbni_softc *, enum sbni_reg);
121 static __inline void	sbni_outb(struct sbni_softc *, enum sbni_reg, u_char);
122 static __inline void	sbni_insb(struct sbni_softc *, u_char *, u_int);
123 static __inline void	sbni_outsb(struct sbni_softc *, u_char *, u_int);
124 
125 static u_int32_t crc32tab[];
126 
127 #ifdef SBNI_DUAL_COMPOUND
128 struct sbni_softc *sbni_headlist;
129 #endif
130 
131 u_int32_t next_sbni_unit;
132 
133 /* -------------------------------------------------------------------------- */
134 
135 static __inline u_char
136 sbni_inb(struct sbni_softc *sc, enum sbni_reg reg)
137 {
138 	return bus_space_read_1(
139 	    rman_get_bustag(sc->io_res),
140 	    rman_get_bushandle(sc->io_res),
141 	    sc->io_off + reg);
142 }
143 
144 static __inline void
145 sbni_outb(struct sbni_softc *sc, enum sbni_reg reg, u_char value)
146 {
147 	bus_space_write_1(
148 	    rman_get_bustag(sc->io_res),
149 	    rman_get_bushandle(sc->io_res),
150 	    sc->io_off + reg, value);
151 }
152 
153 static __inline void
154 sbni_insb(struct sbni_softc *sc, u_char *to, u_int len)
155 {
156 	bus_space_read_multi_1(
157 	    rman_get_bustag(sc->io_res),
158 	    rman_get_bushandle(sc->io_res),
159 	    sc->io_off + DAT, to, len);
160 }
161 
162 static __inline void
163 sbni_outsb(struct sbni_softc *sc, u_char *from, u_int len)
164 {
165 	bus_space_write_multi_1(
166 	    rman_get_bustag(sc->io_res),
167 	    rman_get_bushandle(sc->io_res),
168 	    sc->io_off + DAT, from, len);
169 }
170 
171 
172 /*
173 	Valid combinations in CSR0 (for probing):
174 
175 	VALID_DECODER	0000,0011,1011,1010
176 
177 				    	; 0   ; -
178 				TR_REQ	; 1   ; +
179 			TR_RDY	    	; 2   ; -
180 			TR_RDY	TR_REQ	; 3   ; +
181 		BU_EMP		    	; 4   ; +
182 		BU_EMP	     	TR_REQ	; 5   ; +
183 		BU_EMP	TR_RDY	    	; 6   ; -
184 		BU_EMP	TR_RDY	TR_REQ	; 7   ; +
185 	RC_RDY 		     		; 8   ; +
186 	RC_RDY			TR_REQ	; 9   ; +
187 	RC_RDY		TR_RDY		; 10  ; -
188 	RC_RDY		TR_RDY	TR_REQ	; 11  ; -
189 	RC_RDY	BU_EMP			; 12  ; -
190 	RC_RDY	BU_EMP		TR_REQ	; 13  ; -
191 	RC_RDY	BU_EMP	TR_RDY		; 14  ; -
192 	RC_RDY	BU_EMP	TR_RDY	TR_REQ	; 15  ; -
193 */
194 
195 #define VALID_DECODER	(2 + 8 + 0x10 + 0x20 + 0x80 + 0x100 + 0x200)
196 
197 
198 int
199 sbni_probe(struct sbni_softc *sc)
200 {
201 	u_char csr0;
202 
203 	csr0 = sbni_inb(sc, CSR0);
204 	if (csr0 != 0xff && csr0 != 0x00) {
205 		csr0 &= ~EN_INT;
206 		if (csr0 & BU_EMP)
207 			csr0 |= EN_INT;
208 
209 		if (VALID_DECODER & (1 << (csr0 >> 4)))
210 			return (0);
211 	}
212 
213 	return (ENXIO);
214 }
215 
216 
217 /*
218  * Install interface into kernel networking data structures
219  */
220 void
221 sbni_attach(struct sbni_softc *sc, int unit, struct sbni_flags flags)
222 {
223 	struct ifnet *ifp;
224 	u_char csr0;
225 
226 	ifp = sc->ifp = if_alloc(IFT_ETHER);
227 	if (ifp == NULL)
228 		panic("sbni%d: can not if_alloc()", unit);
229 	sbni_outb(sc, CSR0, 0);
230 	set_initial_values(sc, flags);
231 
232 	callout_handle_init(&sc->wch);
233 	/* Initialize ifnet structure */
234 	ifp->if_softc	= sc;
235 	if_initname(ifp, "sbni", unit);
236 	ifp->if_init	= sbni_init;
237 	ifp->if_start	= sbni_start;
238 	ifp->if_ioctl	= sbni_ioctl;
239 	ifp->if_watchdog	= sbni_watchdog;
240 	ifp->if_snd.ifq_maxlen	= IFQ_MAXLEN;
241 
242 	/* report real baud rate */
243 	csr0 = sbni_inb(sc, CSR0);
244 	ifp->if_baudrate =
245 		(csr0 & 0x01 ? 500000 : 2000000) / (1 << flags.rate);
246 
247 	ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST |
248 	    IFF_NEEDSGIANT;
249 	ether_ifattach(ifp, sc->enaddr);
250 	/* device attach does transition from UNCONFIGURED to IDLE state */
251 
252 	if_printf(ifp, "speed %ld, rxl ", ifp->if_baudrate);
253 	if (sc->delta_rxl)
254 		printf("auto\n");
255 	else
256 		printf("%d (fixed)\n", sc->cur_rxl_index);
257 }
258 
259 /* -------------------------------------------------------------------------- */
260 
261 static void
262 sbni_init(void *xsc)
263 {
264 	struct sbni_softc *sc;
265 	struct ifnet *ifp;
266 	int  s;
267 
268 	sc = (struct sbni_softc *)xsc;
269 	ifp = sc->ifp;
270 
271 	/*
272 	 * kludge to avoid multiple initialization when more than once
273 	 * protocols configured
274 	 */
275 	if (ifp->if_drv_flags & IFF_DRV_RUNNING)
276 		return;
277 
278 	s = splimp();
279 	ifp->if_timer = 0;
280 	card_start(sc);
281 	sc->wch = timeout(sbni_timeout, sc, hz/SBNI_HZ);
282 
283 	ifp->if_drv_flags |= IFF_DRV_RUNNING;
284 	ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
285 
286 	/* attempt to start output */
287 	sbni_start(ifp);
288 	splx(s);
289 }
290 
291 
292 static void
293 sbni_start(struct ifnet *ifp)
294 {
295 	struct sbni_softc *sc = ifp->if_softc;
296 	if (sc->tx_frameno == 0)
297 		prepare_to_send(sc);
298 }
299 
300 
301 static void
302 sbni_stop(struct sbni_softc *sc)
303 {
304 	sbni_outb(sc, CSR0, 0);
305 	drop_xmit_queue(sc);
306 
307 	if (sc->rx_buf_p) {
308 		m_freem(sc->rx_buf_p);
309 		sc->rx_buf_p = NULL;
310 	}
311 
312 	untimeout(sbni_timeout, sc, sc->wch);
313 	sc->wch.callout = NULL;
314 }
315 
316 /* -------------------------------------------------------------------------- */
317 
318 /* interrupt handler */
319 
320 /*
321  * 	SBNI12D-10, -11/ISA boards within "common interrupt" mode could not
322  * be looked as two independent single-channel devices. Every channel seems
323  * as Ethernet interface but interrupt handler must be common. Really, first
324  * channel ("master") driver only registers the handler. In it's struct softc
325  * it has got pointer to "slave" channel's struct softc and handles that's
326  * interrupts too.
327  *	softc of successfully attached ISA SBNI boards is linked to list.
328  * While next board driver is initialized, it scans this list. If one
329  * has found softc with same irq and ioaddr different by 4 then it assumes
330  * this board to be "master".
331  */
332 
333 void
334 sbni_intr(void *arg)
335 {
336 	struct sbni_softc *sc;
337 	int repeat;
338 
339 	sc = (struct sbni_softc *)arg;
340 
341 	do {
342 		repeat = 0;
343 		if (sbni_inb(sc, CSR0) & (RC_RDY | TR_RDY)) {
344 			handle_channel(sc);
345 			repeat = 1;
346 		}
347 		if (sc->slave_sc && 	/* second channel present */
348 		    (sbni_inb(sc->slave_sc, CSR0) & (RC_RDY | TR_RDY))) {
349 			handle_channel(sc->slave_sc);
350 			repeat = 1;
351 		}
352 	} while (repeat);
353 }
354 
355 
356 static void
357 handle_channel(struct sbni_softc *sc)
358 {
359 	int req_ans;
360 	u_char csr0;
361 
362 	sbni_outb(sc, CSR0, (sbni_inb(sc, CSR0) & ~EN_INT) | TR_REQ);
363 
364 	sc->timer_ticks = CHANGE_LEVEL_START_TICKS;
365 	for (;;) {
366 		csr0 = sbni_inb(sc, CSR0);
367 		if ((csr0 & (RC_RDY | TR_RDY)) == 0)
368 			break;
369 
370 		req_ans = !(sc->state & FL_PREV_OK);
371 
372 		if (csr0 & RC_RDY)
373 			req_ans = recv_frame(sc);
374 
375 		/*
376 		 * TR_RDY always equals 1 here because we have owned the marker,
377 		 * and we set TR_REQ when disabled interrupts
378 		 */
379 		csr0 = sbni_inb(sc, CSR0);
380 		if ((csr0 & TR_RDY) == 0 || (csr0 & RC_RDY) != 0)
381 			printf("sbni: internal error!\n");
382 
383 		/* if state & FL_NEED_RESEND != 0 then tx_frameno != 0 */
384 		if (req_ans || sc->tx_frameno != 0)
385 			send_frame(sc);
386 		else {
387 			/* send the marker without any data */
388 			sbni_outb(sc, CSR0, sbni_inb(sc, CSR0) & ~TR_REQ);
389 		}
390 	}
391 
392 	sbni_outb(sc, CSR0, sbni_inb(sc, CSR0) | EN_INT);
393 }
394 
395 
396 /*
397  * Routine returns 1 if it need to acknoweledge received frame.
398  * Empty frame received without errors won't be acknoweledged.
399  */
400 
401 static int
402 recv_frame(struct sbni_softc *sc)
403 {
404 	u_int32_t crc;
405 	u_int framelen, frameno, ack;
406 	u_int is_first, frame_ok;
407 
408 	crc = CRC32_INITIAL;
409 	if (check_fhdr(sc, &framelen, &frameno, &ack, &is_first, &crc)) {
410 		frame_ok = framelen > 4 ?
411 		    upload_data(sc, framelen, frameno, is_first, crc) :
412 		    skip_tail(sc, framelen, crc);
413 		if (frame_ok)
414 			interpret_ack(sc, ack);
415 	} else {
416 		framelen = 0;
417 		frame_ok = 0;
418 	}
419 
420 	sbni_outb(sc, CSR0, sbni_inb(sc, CSR0) ^ CT_ZER);
421 	if (frame_ok) {
422 		sc->state |= FL_PREV_OK;
423 		if (framelen > 4)
424 			sc->in_stats.all_rx_number++;
425 	} else {
426 		sc->state &= ~FL_PREV_OK;
427 		change_level(sc);
428 		sc->in_stats.all_rx_number++;
429 		sc->in_stats.bad_rx_number++;
430 	}
431 
432 	return (!frame_ok || framelen > 4);
433 }
434 
435 
436 static void
437 send_frame(struct sbni_softc *sc)
438 {
439 	u_int32_t crc;
440 	u_char csr0;
441 
442 	crc = CRC32_INITIAL;
443 	if (sc->state & FL_NEED_RESEND) {
444 
445 		/* if frame was sended but not ACK'ed - resend it */
446 		if (sc->trans_errors) {
447 			sc->trans_errors--;
448 			if (sc->framelen != 0)
449 				sc->in_stats.resend_tx_number++;
450 		} else {
451 			/* cannot xmit with many attempts */
452 			drop_xmit_queue(sc);
453 			goto do_send;
454 		}
455 	} else
456 		sc->trans_errors = TR_ERROR_COUNT;
457 
458 	send_frame_header(sc, &crc);
459 	sc->state |= FL_NEED_RESEND;
460 	/*
461 	 * FL_NEED_RESEND will be cleared after ACK, but if empty
462 	 * frame sended then in prepare_to_send next frame
463 	 */
464 
465 
466 	if (sc->framelen) {
467 		download_data(sc, &crc);
468 		sc->in_stats.all_tx_number++;
469 		sc->state |= FL_WAIT_ACK;
470 	}
471 
472 	sbni_outsb(sc, (u_char *)&crc, sizeof crc);
473 
474 do_send:
475 	csr0 = sbni_inb(sc, CSR0);
476 	sbni_outb(sc, CSR0, csr0 & ~TR_REQ);
477 
478 	if (sc->tx_frameno) {
479 		/* next frame exists - request to send */
480 		sbni_outb(sc, CSR0, csr0 | TR_REQ);
481 	}
482 }
483 
484 
485 static void
486 download_data(struct sbni_softc *sc, u_int32_t *crc_p)
487 {
488 	struct mbuf *m;
489 	caddr_t	data_p;
490 	u_int data_len, pos, slice;
491 
492 	data_p = NULL;		/* initialized to avoid warn */
493 	pos = 0;
494 
495 	for (m = sc->tx_buf_p;  m != NULL && pos < sc->pktlen;  m = m->m_next) {
496 		if (pos + m->m_len > sc->outpos) {
497 			data_len = m->m_len - (sc->outpos - pos);
498 			data_p = mtod(m, caddr_t) + (sc->outpos - pos);
499 
500 			goto do_copy;
501 		} else
502 			pos += m->m_len;
503 	}
504 
505 	data_len = 0;
506 
507 do_copy:
508 	pos = 0;
509 	do {
510 		if (data_len) {
511 			slice = min(data_len, sc->framelen - pos);
512 			sbni_outsb(sc, data_p, slice);
513 			*crc_p = calc_crc32(*crc_p, data_p, slice);
514 
515 			pos += slice;
516 			if (data_len -= slice)
517 				data_p += slice;
518 			else {
519 				do {
520 					m = m->m_next;
521 				} while (m != NULL && m->m_len == 0);
522 
523 				if (m) {
524 					data_len = m->m_len;
525 					data_p = mtod(m, caddr_t);
526 				}
527 			}
528 		} else {
529 			/* frame too short - zero padding */
530 
531 			pos = sc->framelen - pos;
532 			while (pos--) {
533 				sbni_outb(sc, DAT, 0);
534 				*crc_p = CRC32(0, *crc_p);
535 			}
536 			return;
537 		}
538 	} while (pos < sc->framelen);
539 }
540 
541 
542 static int
543 upload_data(struct sbni_softc *sc, u_int framelen, u_int frameno,
544 	    u_int is_first, u_int32_t crc)
545 {
546 	int frame_ok;
547 
548 	if (is_first) {
549 		sc->wait_frameno = frameno;
550 		sc->inppos = 0;
551 	}
552 
553 	if (sc->wait_frameno == frameno) {
554 
555 		if (sc->inppos + framelen  <=  ETHER_MAX_LEN) {
556 			frame_ok = append_frame_to_pkt(sc, framelen, crc);
557 
558 		/*
559 		 * if CRC is right but framelen incorrect then transmitter
560 		 * error was occured... drop entire packet
561 		 */
562 		} else if ((frame_ok = skip_tail(sc, framelen, crc)) != 0) {
563 			sc->wait_frameno = 0;
564 			sc->inppos = 0;
565 			sc->ifp->if_ierrors++;
566 			/* now skip all frames until is_first != 0 */
567 		}
568 	} else
569 		frame_ok = skip_tail(sc, framelen, crc);
570 
571 	if (is_first && !frame_ok) {
572 		/*
573 		 * Frame has been violated, but we have stored
574 		 * is_first already... Drop entire packet.
575 		 */
576 		sc->wait_frameno = 0;
577 		sc->ifp->if_ierrors++;
578 	}
579 
580 	return (frame_ok);
581 }
582 
583 
584 static __inline void	send_complete(struct sbni_softc *);
585 
586 static __inline void
587 send_complete(struct sbni_softc *sc)
588 {
589 	m_freem(sc->tx_buf_p);
590 	sc->tx_buf_p = NULL;
591 	sc->ifp->if_opackets++;
592 }
593 
594 
595 static void
596 interpret_ack(struct sbni_softc *sc, u_int ack)
597 {
598 	if (ack == FRAME_SENT_OK) {
599 		sc->state &= ~FL_NEED_RESEND;
600 
601 		if (sc->state & FL_WAIT_ACK) {
602 			sc->outpos += sc->framelen;
603 
604 			if (--sc->tx_frameno) {
605 				sc->framelen = min(
606 				    sc->maxframe, sc->pktlen - sc->outpos);
607 			} else {
608 				send_complete(sc);
609 				prepare_to_send(sc);
610 			}
611 		}
612 	}
613 
614 	sc->state &= ~FL_WAIT_ACK;
615 }
616 
617 
618 /*
619  * Glue received frame with previous fragments of packet.
620  * Indicate packet when last frame would be accepted.
621  */
622 
623 static int
624 append_frame_to_pkt(struct sbni_softc *sc, u_int framelen, u_int32_t crc)
625 {
626 	caddr_t p;
627 
628 	if (sc->inppos + framelen > ETHER_MAX_LEN)
629 		return (0);
630 
631 	if (!sc->rx_buf_p && !get_rx_buf(sc))
632 		return (0);
633 
634 	p = sc->rx_buf_p->m_data + sc->inppos;
635 	sbni_insb(sc, p, framelen);
636 	if (calc_crc32(crc, p, framelen) != CRC32_REMAINDER)
637 		return (0);
638 
639 	sc->inppos += framelen - 4;
640 	if (--sc->wait_frameno == 0) {		/* last frame received */
641 		indicate_pkt(sc);
642 		sc->ifp->if_ipackets++;
643 	}
644 
645 	return (1);
646 }
647 
648 
649 /*
650  * Prepare to start output on adapter. Current priority must be set to splimp
651  * before this routine is called.
652  * Transmitter will be actually activated when marker has been accepted.
653  */
654 
655 static void
656 prepare_to_send(struct sbni_softc *sc)
657 {
658 	struct mbuf *m;
659 	u_int len;
660 
661 	/* sc->tx_buf_p == NULL here! */
662 	if (sc->tx_buf_p)
663 		printf("sbni: memory leak!\n");
664 
665 	sc->outpos = 0;
666 	sc->state &= ~(FL_WAIT_ACK | FL_NEED_RESEND);
667 
668 	for (;;) {
669 		IF_DEQUEUE(&sc->ifp->if_snd, sc->tx_buf_p);
670 		if (!sc->tx_buf_p) {
671 			/* nothing to transmit... */
672 			sc->pktlen     = 0;
673 			sc->tx_frameno = 0;
674 			sc->framelen   = 0;
675 			sc->ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
676 			return;
677 		}
678 
679 		for (len = 0, m = sc->tx_buf_p;  m;  m = m->m_next)
680 			len += m->m_len;
681 
682 		if (len != 0)
683 			break;
684 		m_freem(sc->tx_buf_p);
685 	}
686 
687 	if (len < SBNI_MIN_LEN)
688 		len = SBNI_MIN_LEN;
689 
690 	sc->pktlen	= len;
691 	sc->tx_frameno	= (len + sc->maxframe - 1) / sc->maxframe;
692 	sc->framelen	= min(len, sc->maxframe);
693 
694 	sbni_outb(sc, CSR0, sbni_inb(sc, CSR0) | TR_REQ);
695 	sc->ifp->if_drv_flags |= IFF_DRV_OACTIVE;
696 	BPF_MTAP(sc->ifp, sc->tx_buf_p);
697 }
698 
699 
700 static void
701 drop_xmit_queue(struct sbni_softc *sc)
702 {
703 	struct mbuf *m;
704 
705 	if (sc->tx_buf_p) {
706 		m_freem(sc->tx_buf_p);
707 		sc->tx_buf_p = NULL;
708 		sc->ifp->if_oerrors++;
709 	}
710 
711 	for (;;) {
712 		IF_DEQUEUE(&sc->ifp->if_snd, m);
713 		if (m == NULL)
714 			break;
715 		m_freem(m);
716 		sc->ifp->if_oerrors++;
717 	}
718 
719 	sc->tx_frameno	= 0;
720 	sc->framelen	= 0;
721 	sc->outpos	= 0;
722 	sc->state &= ~(FL_WAIT_ACK | FL_NEED_RESEND);
723 	sc->ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
724 }
725 
726 
727 static void
728 send_frame_header(struct sbni_softc *sc, u_int32_t *crc_p)
729 {
730 	u_int32_t crc;
731 	u_int len_field;
732 	u_char value;
733 
734 	crc = *crc_p;
735 	len_field = sc->framelen + 6;	/* CRC + frameno + reserved */
736 
737 	if (sc->state & FL_NEED_RESEND)
738 		len_field |= FRAME_RETRY;	/* non-first attempt... */
739 
740 	if (sc->outpos == 0)
741 		len_field |= FRAME_FIRST;
742 
743 	len_field |= (sc->state & FL_PREV_OK) ? FRAME_SENT_OK : FRAME_SENT_BAD;
744 	sbni_outb(sc, DAT, SBNI_SIG);
745 
746 	value = (u_char)len_field;
747 	sbni_outb(sc, DAT, value);
748 	crc = CRC32(value, crc);
749 	value = (u_char)(len_field >> 8);
750 	sbni_outb(sc, DAT, value);
751 	crc = CRC32(value, crc);
752 
753 	sbni_outb(sc, DAT, sc->tx_frameno);
754 	crc = CRC32(sc->tx_frameno, crc);
755 	sbni_outb(sc, DAT, 0);
756 	crc = CRC32(0, crc);
757 	*crc_p = crc;
758 }
759 
760 
761 /*
762  * if frame tail not needed (incorrect number or received twice),
763  * it won't store, but CRC will be calculated
764  */
765 
766 static int
767 skip_tail(struct sbni_softc *sc, u_int tail_len, u_int32_t crc)
768 {
769 	while (tail_len--)
770 		crc = CRC32(sbni_inb(sc, DAT), crc);
771 
772 	return (crc == CRC32_REMAINDER);
773 }
774 
775 
776 static int
777 check_fhdr(struct sbni_softc *sc, u_int *framelen, u_int *frameno,
778 	   u_int *ack, u_int *is_first, u_int32_t *crc_p)
779 {
780 	u_int32_t crc;
781 	u_char value;
782 
783 	crc = *crc_p;
784 	if (sbni_inb(sc, DAT) != SBNI_SIG)
785 		return (0);
786 
787 	value = sbni_inb(sc, DAT);
788 	*framelen = (u_int)value;
789 	crc = CRC32(value, crc);
790 	value = sbni_inb(sc, DAT);
791 	*framelen |= ((u_int)value) << 8;
792 	crc = CRC32(value, crc);
793 
794 	*ack = *framelen & FRAME_ACK_MASK;
795 	*is_first = (*framelen & FRAME_FIRST) != 0;
796 
797 	if ((*framelen &= FRAME_LEN_MASK) < 6 || *framelen > SBNI_MAX_FRAME - 3)
798 		return (0);
799 
800 	value = sbni_inb(sc, DAT);
801 	*frameno = (u_int)value;
802 	crc = CRC32(value, crc);
803 
804 	crc = CRC32(sbni_inb(sc, DAT), crc);		/* reserved byte */
805 	*framelen -= 2;
806 
807 	*crc_p = crc;
808 	return (1);
809 }
810 
811 
812 static int
813 get_rx_buf(struct sbni_softc *sc)
814 {
815 	struct mbuf *m;
816 
817 	MGETHDR(m, M_DONTWAIT, MT_DATA);
818 	if (m == NULL) {
819 		if_printf(sc->ifp, "cannot allocate header mbuf\n");
820 		return (0);
821 	}
822 
823 	/*
824 	 * We always put the received packet in a single buffer -
825 	 * either with just an mbuf header or in a cluster attached
826 	 * to the header. The +2 is to compensate for the alignment
827 	 * fixup below.
828 	 */
829 	if (ETHER_MAX_LEN + 2 > MHLEN) {
830 		/* Attach an mbuf cluster */
831 		MCLGET(m, M_DONTWAIT);
832 		if ((m->m_flags & M_EXT) == 0) {
833 			m_freem(m);
834 			return (0);
835 		}
836 	}
837 	m->m_pkthdr.len = m->m_len = ETHER_MAX_LEN + 2;
838 
839 	/*
840 	 * The +2 is to longword align the start of the real packet.
841 	 * (sizeof ether_header == 14)
842 	 * This is important for NFS.
843 	 */
844 	m_adj(m, 2);
845 	sc->rx_buf_p = m;
846 	return (1);
847 }
848 
849 
850 static void
851 indicate_pkt(struct sbni_softc *sc)
852 {
853 	struct ifnet *ifp = sc->ifp;
854 	struct mbuf *m;
855 
856 	m = sc->rx_buf_p;
857 	m->m_pkthdr.rcvif = ifp;
858 	m->m_pkthdr.len   = m->m_len = sc->inppos;
859 
860 	(*ifp->if_input)(ifp, m);
861 	sc->rx_buf_p = NULL;
862 }
863 
864 /* -------------------------------------------------------------------------- */
865 
866 /*
867  * Routine checks periodically wire activity and regenerates marker if
868  * connect was inactive for a long time.
869  */
870 
871 static void
872 sbni_timeout(void *xsc)
873 {
874 	struct sbni_softc *sc;
875 	int s;
876 	u_char csr0;
877 
878 	sc = (struct sbni_softc *)xsc;
879 	s = splimp();
880 
881 	csr0 = sbni_inb(sc, CSR0);
882 	if (csr0 & RC_CHK) {
883 
884 		if (sc->timer_ticks) {
885 			if (csr0 & (RC_RDY | BU_EMP))
886 				/* receiving not active */
887 				sc->timer_ticks--;
888 		} else {
889 			sc->in_stats.timeout_number++;
890 			if (sc->delta_rxl)
891 				timeout_change_level(sc);
892 
893 			sbni_outb(sc, CSR1, *(u_char *)&sc->csr1 | PR_RES);
894 			csr0 = sbni_inb(sc, CSR0);
895 		}
896 	}
897 
898 	sbni_outb(sc, CSR0, csr0 | RC_CHK);
899 	sc->wch = timeout(sbni_timeout, sc, hz/SBNI_HZ);
900 	splx(s);
901 }
902 
903 /* -------------------------------------------------------------------------- */
904 
905 static void
906 card_start(struct sbni_softc *sc)
907 {
908 	sc->timer_ticks = CHANGE_LEVEL_START_TICKS;
909 	sc->state &= ~(FL_WAIT_ACK | FL_NEED_RESEND);
910 	sc->state |= FL_PREV_OK;
911 
912 	sc->inppos = 0;
913 	sc->wait_frameno = 0;
914 
915 	sbni_outb(sc, CSR1, *(u_char *)&sc->csr1 | PR_RES);
916 	sbni_outb(sc, CSR0, EN_INT);
917 }
918 
919 /* -------------------------------------------------------------------------- */
920 
921 /*
922  * Device timeout/watchdog routine. Entered if the device neglects to
923  *	generate an interrupt after a transmit has been started on it.
924  */
925 
926 static void
927 sbni_watchdog(struct ifnet *ifp)
928 {
929 	log(LOG_ERR, "%s: device timeout\n", ifp->if_xname);
930 	ifp->if_oerrors++;
931 }
932 
933 
934 static u_char rxl_tab[] = {
935 	0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x08,
936 	0x0a, 0x0c, 0x0f, 0x16, 0x18, 0x1a, 0x1c, 0x1f
937 };
938 
939 #define SIZE_OF_TIMEOUT_RXL_TAB 4
940 static u_char timeout_rxl_tab[] = {
941 	0x03, 0x05, 0x08, 0x0b
942 };
943 
944 static void
945 set_initial_values(struct sbni_softc *sc, struct sbni_flags flags)
946 {
947 	if (flags.fixed_rxl) {
948 		sc->delta_rxl = 0; /* disable receive level autodetection */
949 		sc->cur_rxl_index = flags.rxl;
950 	} else {
951 		sc->delta_rxl = DEF_RXL_DELTA;
952 		sc->cur_rxl_index = DEF_RXL;
953 	}
954 
955 	sc->csr1.rate = flags.fixed_rate ? flags.rate : DEFAULT_RATE;
956 	sc->csr1.rxl  = rxl_tab[sc->cur_rxl_index];
957 	sc->maxframe  = DEFAULT_FRAME_LEN;
958 
959 	/*
960 	 * generate Ethernet address (0x00ff01xxxxxx)
961 	 */
962 	*(u_int16_t *) sc->enaddr = htons(0x00ff);
963 	if (flags.mac_addr) {
964 		*(u_int32_t *) (sc->enaddr + 2) =
965 		    htonl(flags.mac_addr | 0x01000000);
966 	} else {
967 		*(u_char *) (sc->enaddr + 2) = 0x01;
968 		read_random(sc->enaddr + 3, 3);
969 	}
970 }
971 
972 
973 #ifdef SBNI_DUAL_COMPOUND
974 
975 struct sbni_softc *
976 connect_to_master(struct sbni_softc *sc)
977 {
978 	struct sbni_softc *p, *p_prev;
979 
980 	for (p = sbni_headlist, p_prev = NULL; p; p_prev = p, p = p->link) {
981 		if (rman_get_start(p->io_res) == rman_get_start(sc->io_res) + 4 ||
982 		    rman_get_start(p->io_res) == rman_get_start(sc->io_res) - 4) {
983 			p->slave_sc = sc;
984 			if (p_prev)
985 				p_prev->link = p->link;
986 			else
987 				sbni_headlist = p->link;
988 			return p;
989 		}
990 	}
991 
992 	return (NULL);
993 }
994 
995 #endif	/* SBNI_DUAL_COMPOUND */
996 
997 
998 /* Receive level auto-selection */
999 
1000 static void
1001 change_level(struct sbni_softc *sc)
1002 {
1003 	if (sc->delta_rxl == 0)		/* do not auto-negotiate RxL */
1004 		return;
1005 
1006 	if (sc->cur_rxl_index == 0)
1007 		sc->delta_rxl = 1;
1008 	else if (sc->cur_rxl_index == 15)
1009 		sc->delta_rxl = -1;
1010 	else if (sc->cur_rxl_rcvd < sc->prev_rxl_rcvd)
1011 		sc->delta_rxl = -sc->delta_rxl;
1012 
1013 	sc->csr1.rxl = rxl_tab[sc->cur_rxl_index += sc->delta_rxl];
1014 	sbni_inb(sc, CSR0);	/* it needed for PCI cards */
1015 	sbni_outb(sc, CSR1, *(u_char *)&sc->csr1);
1016 
1017 	sc->prev_rxl_rcvd = sc->cur_rxl_rcvd;
1018 	sc->cur_rxl_rcvd  = 0;
1019 }
1020 
1021 
1022 static void
1023 timeout_change_level(struct sbni_softc *sc)
1024 {
1025 	sc->cur_rxl_index = timeout_rxl_tab[sc->timeout_rxl];
1026 	if (++sc->timeout_rxl >= 4)
1027 		sc->timeout_rxl = 0;
1028 
1029 	sc->csr1.rxl = rxl_tab[sc->cur_rxl_index];
1030 	sbni_inb(sc, CSR0);
1031 	sbni_outb(sc, CSR1, *(u_char *)&sc->csr1);
1032 
1033 	sc->prev_rxl_rcvd = sc->cur_rxl_rcvd;
1034 	sc->cur_rxl_rcvd  = 0;
1035 }
1036 
1037 /* -------------------------------------------------------------------------- */
1038 
1039 /*
1040  * Process an ioctl request. This code needs some work - it looks
1041  *	pretty ugly.
1042  */
1043 
1044 static int
1045 sbni_ioctl(struct ifnet *ifp, u_long command, caddr_t data)
1046 {
1047 	struct sbni_softc *sc;
1048 	struct ifreq *ifr;
1049 	struct thread *td;
1050 	struct sbni_in_stats *in_stats;
1051 	struct sbni_flags flags;
1052 	int error, s;
1053 
1054 	sc = ifp->if_softc;
1055 	ifr = (struct ifreq *)data;
1056 	td = curthread;
1057 	error = 0;
1058 
1059 	s = splimp();
1060 
1061 	switch (command) {
1062 	case SIOCSIFFLAGS:
1063 		/*
1064 		 * If the interface is marked up and stopped, then start it.
1065 		 * If it is marked down and running, then stop it.
1066 		 */
1067 		if (ifp->if_flags & IFF_UP) {
1068 			if (!(ifp->if_drv_flags & IFF_DRV_RUNNING))
1069 				sbni_init(sc);
1070 		} else {
1071 			if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
1072 				sbni_stop(sc);
1073 				ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
1074 			}
1075 		}
1076 		break;
1077 
1078 	case SIOCADDMULTI:
1079 	case SIOCDELMULTI:
1080 		/*
1081 		 * Multicast list has changed; set the hardware filter
1082 		 * accordingly.
1083 		 */
1084 		error = 0;
1085 		/* if (ifr == NULL)
1086 			error = EAFNOSUPPORT; */
1087 		break;
1088 
1089 	case SIOCSIFMTU:
1090 		if (ifr->ifr_mtu > ETHERMTU)
1091 			error = EINVAL;
1092 		else
1093 			ifp->if_mtu = ifr->ifr_mtu;
1094 		break;
1095 
1096 		/*
1097 		 * SBNI specific ioctl
1098 		 */
1099 	case SIOCGHWFLAGS:	/* get flags */
1100 		bcopy((caddr_t)IF_LLADDR(sc->ifp)+3, (caddr_t) &flags, 3);
1101 		flags.rxl = sc->cur_rxl_index;
1102 		flags.rate = sc->csr1.rate;
1103 		flags.fixed_rxl = (sc->delta_rxl == 0);
1104 		flags.fixed_rate = 1;
1105 		ifr->ifr_data = *(caddr_t*) &flags;
1106 		break;
1107 
1108 	case SIOCGINSTATS:
1109 		in_stats = (struct sbni_in_stats *)ifr->ifr_data;
1110 		bcopy((void *)(&(sc->in_stats)), (void *)in_stats,
1111 		      sizeof(struct sbni_in_stats));
1112 		break;
1113 
1114 	case SIOCSHWFLAGS:	/* set flags */
1115 		/* root only */
1116 		error = priv_check(td, PRIV_DRIVER);
1117 		if (error)
1118 			break;
1119 		flags = *(struct sbni_flags*)&ifr->ifr_data;
1120 		if (flags.fixed_rxl) {
1121 			sc->delta_rxl = 0;
1122 			sc->cur_rxl_index = flags.rxl;
1123 		} else {
1124 			sc->delta_rxl = DEF_RXL_DELTA;
1125 			sc->cur_rxl_index = DEF_RXL;
1126 		}
1127 		sc->csr1.rxl = rxl_tab[sc->cur_rxl_index];
1128 		sc->csr1.rate = flags.fixed_rate ? flags.rate : DEFAULT_RATE;
1129 		if (flags.mac_addr)
1130 			bcopy((caddr_t) &flags,
1131 			      (caddr_t) IF_LLADDR(sc->ifp)+3, 3);
1132 
1133 		/* Don't be afraid... */
1134 		sbni_outb(sc, CSR1, *(char*)(&sc->csr1) | PR_RES);
1135 		break;
1136 
1137 	case SIOCRINSTATS:
1138 		if (!(error = priv_check(td, PRIV_DRIVER)))	/* root only */
1139 			bzero(&sc->in_stats, sizeof(struct sbni_in_stats));
1140 		break;
1141 
1142 	default:
1143 		error = ether_ioctl(ifp, command, data);
1144 		break;
1145 	}
1146 
1147 	splx(s);
1148 	return (error);
1149 }
1150 
1151 /* -------------------------------------------------------------------------- */
1152 
1153 #ifdef ASM_CRC
1154 
1155 static u_int32_t
1156 calc_crc32(u_int32_t crc, caddr_t p, u_int len)
1157 {
1158 	register u_int32_t  _crc __asm ("ax");
1159 	_crc = crc;
1160 
1161 	__asm __volatile (
1162 		"xorl	%%ebx, %%ebx\n"
1163 		"movl	%1, %%esi\n"
1164 		"movl	%2, %%ecx\n"
1165 		"movl	$crc32tab, %%edi\n"
1166 		"shrl	$2, %%ecx\n"
1167 		"jz	1f\n"
1168 
1169 		".align 4\n"
1170 	"0:\n"
1171 		"movb	%%al, %%bl\n"
1172 		"movl	(%%esi), %%edx\n"
1173 		"shrl	$8, %%eax\n"
1174 		"xorb	%%dl, %%bl\n"
1175 		"shrl	$8, %%edx\n"
1176 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1177 
1178 		"movb	%%al, %%bl\n"
1179 		"shrl	$8, %%eax\n"
1180 		"xorb	%%dl, %%bl\n"
1181 		"shrl	$8, %%edx\n"
1182 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1183 
1184 		"movb	%%al, %%bl\n"
1185 		"shrl	$8, %%eax\n"
1186 		"xorb	%%dl, %%bl\n"
1187 		"movb	%%dh, %%dl\n"
1188 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1189 
1190 		"movb	%%al, %%bl\n"
1191 		"shrl	$8, %%eax\n"
1192 		"xorb	%%dl, %%bl\n"
1193 		"addl	$4, %%esi\n"
1194 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1195 
1196 		"decl	%%ecx\n"
1197 		"jnz	0b\n"
1198 
1199 	"1:\n"
1200 		"movl	%2, %%ecx\n"
1201 		"andl	$3, %%ecx\n"
1202 		"jz	2f\n"
1203 
1204 		"movb	%%al, %%bl\n"
1205 		"shrl	$8, %%eax\n"
1206 		"xorb	(%%esi), %%bl\n"
1207 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1208 
1209 		"decl	%%ecx\n"
1210 		"jz	2f\n"
1211 
1212 		"movb	%%al, %%bl\n"
1213 		"shrl	$8, %%eax\n"
1214 		"xorb	1(%%esi), %%bl\n"
1215 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1216 
1217 		"decl	%%ecx\n"
1218 		"jz	2f\n"
1219 
1220 		"movb	%%al, %%bl\n"
1221 		"shrl	$8, %%eax\n"
1222 		"xorb	2(%%esi), %%bl\n"
1223 		"xorl	(%%edi,%%ebx,4), %%eax\n"
1224 	"2:\n"
1225 		: "=a" (_crc)
1226 		: "g" (p), "g" (len)
1227 		: "bx", "cx", "dx", "si", "di"
1228 	);
1229 
1230 	return (_crc);
1231 }
1232 
1233 #else	/* ASM_CRC */
1234 
1235 static u_int32_t
1236 calc_crc32(u_int32_t crc, caddr_t p, u_int len)
1237 {
1238 	while (len--)
1239 		crc = CRC32(*p++, crc);
1240 
1241 	return (crc);
1242 }
1243 
1244 #endif	/* ASM_CRC */
1245 
1246 
1247 static u_int32_t crc32tab[] __aligned(8) = {
1248 	0xD202EF8D,  0xA505DF1B,  0x3C0C8EA1,  0x4B0BBE37,
1249 	0xD56F2B94,  0xA2681B02,  0x3B614AB8,  0x4C667A2E,
1250 	0xDCD967BF,  0xABDE5729,  0x32D70693,  0x45D03605,
1251 	0xDBB4A3A6,  0xACB39330,  0x35BAC28A,  0x42BDF21C,
1252 	0xCFB5FFE9,  0xB8B2CF7F,  0x21BB9EC5,  0x56BCAE53,
1253 	0xC8D83BF0,  0xBFDF0B66,  0x26D65ADC,  0x51D16A4A,
1254 	0xC16E77DB,  0xB669474D,  0x2F6016F7,  0x58672661,
1255 	0xC603B3C2,  0xB1048354,  0x280DD2EE,  0x5F0AE278,
1256 	0xE96CCF45,  0x9E6BFFD3,  0x0762AE69,  0x70659EFF,
1257 	0xEE010B5C,  0x99063BCA,  0x000F6A70,  0x77085AE6,
1258 	0xE7B74777,  0x90B077E1,  0x09B9265B,  0x7EBE16CD,
1259 	0xE0DA836E,  0x97DDB3F8,  0x0ED4E242,  0x79D3D2D4,
1260 	0xF4DBDF21,  0x83DCEFB7,  0x1AD5BE0D,  0x6DD28E9B,
1261 	0xF3B61B38,  0x84B12BAE,  0x1DB87A14,  0x6ABF4A82,
1262 	0xFA005713,  0x8D076785,  0x140E363F,  0x630906A9,
1263 	0xFD6D930A,  0x8A6AA39C,  0x1363F226,  0x6464C2B0,
1264 	0xA4DEAE1D,  0xD3D99E8B,  0x4AD0CF31,  0x3DD7FFA7,
1265 	0xA3B36A04,  0xD4B45A92,  0x4DBD0B28,  0x3ABA3BBE,
1266 	0xAA05262F,  0xDD0216B9,  0x440B4703,  0x330C7795,
1267 	0xAD68E236,  0xDA6FD2A0,  0x4366831A,  0x3461B38C,
1268 	0xB969BE79,  0xCE6E8EEF,  0x5767DF55,  0x2060EFC3,
1269 	0xBE047A60,  0xC9034AF6,  0x500A1B4C,  0x270D2BDA,
1270 	0xB7B2364B,  0xC0B506DD,  0x59BC5767,  0x2EBB67F1,
1271 	0xB0DFF252,  0xC7D8C2C4,  0x5ED1937E,  0x29D6A3E8,
1272 	0x9FB08ED5,  0xE8B7BE43,  0x71BEEFF9,  0x06B9DF6F,
1273 	0x98DD4ACC,  0xEFDA7A5A,  0x76D32BE0,  0x01D41B76,
1274 	0x916B06E7,  0xE66C3671,  0x7F6567CB,  0x0862575D,
1275 	0x9606C2FE,  0xE101F268,  0x7808A3D2,  0x0F0F9344,
1276 	0x82079EB1,  0xF500AE27,  0x6C09FF9D,  0x1B0ECF0B,
1277 	0x856A5AA8,  0xF26D6A3E,  0x6B643B84,  0x1C630B12,
1278 	0x8CDC1683,  0xFBDB2615,  0x62D277AF,  0x15D54739,
1279 	0x8BB1D29A,  0xFCB6E20C,  0x65BFB3B6,  0x12B88320,
1280 	0x3FBA6CAD,  0x48BD5C3B,  0xD1B40D81,  0xA6B33D17,
1281 	0x38D7A8B4,  0x4FD09822,  0xD6D9C998,  0xA1DEF90E,
1282 	0x3161E49F,  0x4666D409,  0xDF6F85B3,  0xA868B525,
1283 	0x360C2086,  0x410B1010,  0xD80241AA,  0xAF05713C,
1284 	0x220D7CC9,  0x550A4C5F,  0xCC031DE5,  0xBB042D73,
1285 	0x2560B8D0,  0x52678846,  0xCB6ED9FC,  0xBC69E96A,
1286 	0x2CD6F4FB,  0x5BD1C46D,  0xC2D895D7,  0xB5DFA541,
1287 	0x2BBB30E2,  0x5CBC0074,  0xC5B551CE,  0xB2B26158,
1288 	0x04D44C65,  0x73D37CF3,  0xEADA2D49,  0x9DDD1DDF,
1289 	0x03B9887C,  0x74BEB8EA,  0xEDB7E950,  0x9AB0D9C6,
1290 	0x0A0FC457,  0x7D08F4C1,  0xE401A57B,  0x930695ED,
1291 	0x0D62004E,  0x7A6530D8,  0xE36C6162,  0x946B51F4,
1292 	0x19635C01,  0x6E646C97,  0xF76D3D2D,  0x806A0DBB,
1293 	0x1E0E9818,  0x6909A88E,  0xF000F934,  0x8707C9A2,
1294 	0x17B8D433,  0x60BFE4A5,  0xF9B6B51F,  0x8EB18589,
1295 	0x10D5102A,  0x67D220BC,  0xFEDB7106,  0x89DC4190,
1296 	0x49662D3D,  0x3E611DAB,  0xA7684C11,  0xD06F7C87,
1297 	0x4E0BE924,  0x390CD9B2,  0xA0058808,  0xD702B89E,
1298 	0x47BDA50F,  0x30BA9599,  0xA9B3C423,  0xDEB4F4B5,
1299 	0x40D06116,  0x37D75180,  0xAEDE003A,  0xD9D930AC,
1300 	0x54D13D59,  0x23D60DCF,  0xBADF5C75,  0xCDD86CE3,
1301 	0x53BCF940,  0x24BBC9D6,  0xBDB2986C,  0xCAB5A8FA,
1302 	0x5A0AB56B,  0x2D0D85FD,  0xB404D447,  0xC303E4D1,
1303 	0x5D677172,  0x2A6041E4,  0xB369105E,  0xC46E20C8,
1304 	0x72080DF5,  0x050F3D63,  0x9C066CD9,  0xEB015C4F,
1305 	0x7565C9EC,  0x0262F97A,  0x9B6BA8C0,  0xEC6C9856,
1306 	0x7CD385C7,  0x0BD4B551,  0x92DDE4EB,  0xE5DAD47D,
1307 	0x7BBE41DE,  0x0CB97148,  0x95B020F2,  0xE2B71064,
1308 	0x6FBF1D91,  0x18B82D07,  0x81B17CBD,  0xF6B64C2B,
1309 	0x68D2D988,  0x1FD5E91E,  0x86DCB8A4,  0xF1DB8832,
1310 	0x616495A3,  0x1663A535,  0x8F6AF48F,  0xF86DC419,
1311 	0x660951BA,  0x110E612C,  0x88073096,  0xFF000000
1312 };
1313