+ if (eh->ether_type > 1500)
+ goto dropanyway;
+ l = mtod(m, struct llc *);
+ switch (l->llc_control) {
+ case LLC_UI:
+ /* LLC_UI_P forbidden in class 1 service */
+ if ((l->llc_dsap == LLC_ISO_LSAP) &&
+ (l->llc_ssap == LLC_ISO_LSAP)) {
+#ifdef ISO
+ /* LSAP for ISO */
+ m->m_data += 3;
+ m->m_len -= 3;
+ if (m->m_flags & M_PKTHDR)
+ m->m_pkthdr.len -= 3;
+ DEBUGF(undebug & 0x2, printf("clnp packet\n");)
+ schednetisr(NETISR_CLNP);
+ inq = &clnlintrq;
+ if (IF_QFULL(inq)){
+ DEBUGF(undebug & 0x2, printf(" qfull\n");)
+ IF_DROP(inq);
+ m_freem(m);
+ } else {
+ IF_ENQUEUE(inq, m);
+ DEBUGF(undebug & 0x2, printf(" queued\n");)
+ }
+ return;
+#endif ISO
+ }
+ break;
+ case LLC_XID:
+ case LLC_XID_P:
+ if(m->m_len < 6)
+ goto dropanyway;
+ l->llc_window = 0;
+ l->llc_fid = 9;
+ l->llc_class = 1;
+ l->llc_dsap = l->llc_ssap = 0;
+ /* Fall through to */
+ case LLC_TEST:
+ case LLC_TEST_P:
+ {
+ struct sockaddr sa;
+ register struct ether_header *eh2;
+ int i;
+ u_char c = l->llc_dsap;
+ l->llc_dsap = l->llc_ssap;
+ l->llc_ssap = c;
+ sa.sa_family = AF_UNSPEC;
+ eh2 = (struct ether_header *)sa.sa_data;
+ for (i = 0; i < 6; i++) {
+ eh2->ether_shost[i] = c = eh->ether_dhost[i];
+ eh2->ether_dhost[i] =
+ eh->ether_dhost[i] = eh->ether_shost[i];
+ eh->ether_shost[i] = c;
+ }
+ ifp->if_output(ifp, m, &sa);
+ return;
+ }
+ dropanyway:
+ default:
+ m_freem(m);
+ return;
+ }