int isdn_concap_dl_disconn_req(struct concap_proto *concap) { IX25DEBUG( "isdn_concap_dl_disconn_req: %s \n", concap -> net_dev -> name); isdn_net_hangup( concap -> net_dev ); return 0; }
int dw_abc_udp_test(struct sk_buff *skb,struct net_device *ndev) { if(ndev != NULL && skb != NULL && skb->protocol == htons(ETH_P_IP)) { struct iphdr *iph = (struct iphdr *)skb->data; isdn_net_local *lp = (isdn_net_local *) ndev->priv; int rklen = skb->len; if (skb->nh.raw > skb->data && skb->nh.raw < skb->tail) { rklen -= (char *)skb->nh.raw - (char *)skb->data; iph = (struct iphdr *)skb->nh.raw; } if(rklen >= 20 && iph->version == 4 && !(lp->dw_abc_flags & ISDN_DW_ABC_FLAG_NO_UDP_CHECK)) { if( iph->tot_len == NBYTEORDER_30BYTES && iph->protocol == IPPROTO_UDP) { struct udphdr *udp = (struct udphdr *)((char *)iph + (iph->ihl << 2)); ushort usrc = ntohs(udp->source); if( udp->dest == htons(25001) && usrc >= 20000 && usrc < 25000) { char *p = (char *)(udp + 1); if(p[0] == p[1]) { char mc = 0; switch(*p) { case 0x30: mc = *p; if((lp->flags & ISDN_NET_CONNECTED) && (!lp->dialstate)) mc++; break; case 0x32: mc = *p; #ifdef CONFIG_ISDN_WITH_ABC_UDP_CHECK_DIAL if((lp->flags & ISDN_NET_CONNECTED) && (!lp->dialstate)) { mc++; break; } if(!isdn_net_force_dial_lp(lp)) mc++; #endif break; case 0x11: mc = *p + 1; isdn_dw_abc_reset_interface(lp,1); break; case 0x28: mc = *p + 1; break; case 0x2a: case 0x2c: mc = *p; #ifdef CONFIG_ISDN_WITH_ABC_UDP_CHECK_HANGUP if(!(lp->dw_abc_flags & ISDN_DW_ABC_FLAG_NO_UDP_HANGUP)) { if(lp->isdn_device >= 0) { isdn_net_hangup(ndev); mc = *p + 1; } } #endif break; } if(mc) { struct sk_buff *nskb; int need = 2+sizeof(struct iphdr)+sizeof(struct udphdr); int hneed = need + ndev->hard_header_len; if((nskb = (struct sk_buff *)dev_alloc_skb(hneed)) != NULL) { ushort n = sizeof(struct udphdr) + 2; struct iphdr *niph; struct udphdr *nup; skb_reserve(nskb,ndev->hard_header_len); if((niph = (struct iphdr *)skb_put(nskb,need))==NULL){ printk(KERN_DEBUG "%s: skb_put failt (%d bytes)\n", lp->name,hneed); dev_kfree_skb(nskb); return(0); } nup = (struct udphdr *)(niph + 1); ((char *)(nup + 1))[0] = mc; ((char *)(nup + 1))[1] = mc; nup->source=udp->dest; nup->dest=udp->source; nup->len=htons(n); nup->check=0; /* dont need checksum */ memset((void *)niph,0,sizeof(*niph)); niph->version=4; niph->ihl=5; niph->tot_len=NBYTEORDER_30BYTES; niph->ttl = 32; niph->protocol = IPPROTO_UDP; niph->saddr=iph->daddr; niph->daddr=iph->saddr; niph->id=iph->id; niph->check=ip_fast_csum((unsigned char *)niph,niph->ihl); nskb->dev = ndev; nskb->pkt_type = PACKET_HOST; nskb->protocol = htons(ETH_P_IP); nskb->mac.raw = nskb->data; netif_rx(nskb); } return(1); } } } } } } return(0); }