Ejemplo n.º 1
0
Archivo: arp.c Proyecto: gk969/sjIP
// 接收处理ARP帧
void arp_accept(u8 *data, u32 plen)
{
    arp_frm *arp_recv = (arp_frm *)data;

    if(plen >= ARP_FRMLEN)
    {

        ARP_DBP("Recv %d.%d.%d.%d ARP ", arp_recv->src_ip.inb[0], arp_recv->src_ip.inb[1], arp_recv->src_ip.inb[2], arp_recv->src_ip.inb[3]);

        // 添加源IP、MAC至ARP缓存表
        arp_addlist(arp_recv->src_ip.inw, arp_recv->src_mac);

        if(htons(arp_recv->operation) == ARP_TYPE_REQ)
        {
            ARP_DBP("Request %d.%d.%d.%d\r\n", arp_recv->dst_ip.inb[0], arp_recv->dst_ip.inb[1], arp_recv->dst_ip.inb[2], arp_recv->dst_ip.inb[3]);


            if(arp_recv->dst_ip.inw == local.ip.inw)
            {
                ARP_DBP("Req Local IP. ARP Reply\r\n");
                arp_reply(arp_recv);
            }
        }
        else if(htons(arp_recv->operation) == ARP_TYPE_REP)
        {
            ARP_DBP("Reply\r\n");
        }
    }
}
Ejemplo n.º 2
0
//----------------------------------------------------------------------------
//Check Packet and call Stack for TCP or UDP
void check_packet (void)
{
    struct Ethernet_Header *ethernet;    //Pointer auf Ethernet_Header
    struct IP_Header       *ip;          //Pointer auf IP_Header
    struct TCP_Header      *tcp;         //Pointer auf TCP_Header
    struct ICMP_Header     *icmp;        //Pointer auf ICMP_Header

    ethernet = (struct Ethernet_Header *)&eth_buffer[ETHER_OFFSET];
    ip       = (struct IP_Header       *)&eth_buffer[IP_OFFSET];
    tcp      = (struct TCP_Header      *)&eth_buffer[TCP_OFFSET];
    icmp     = (struct ICMP_Header     *)&eth_buffer[ICMP_OFFSET];
    
    if(ethernet->EnetPacketType == HTONS(0x0806) )     //ARP
    {
        arp_reply(); // check arp packet request/reply
    }
    else
    {
        if( ethernet->EnetPacketType == HTONS(0x0800) )  // if IP
        {              
            if( ip->IP_Destaddr == *((unsigned long*)&myip[0]) )  // if my IP address 
            {
                arp_entry_add();  ///Refresh des ARP Eintrages
                if(ip->IP_Proto == PROT_ICMP)
                {
                    switch ( icmp->ICMP_Type )
                    {
                        case (8): //Ping reqest
                            icmp_send(ip->IP_Srcaddr,0,0,icmp->ICMP_SeqNum,icmp->ICMP_Id); 
                            break;
                            
                        case (0): //Ping reply
                            if ((*((unsigned long*)&ping.ip1[0])) == ip->IP_Srcaddr)
                            {
                                ping.result |= 0x01;
                            }
                            DEBUG("%i",    (ip->IP_Srcaddr&0x000000FF)     );
                            DEBUG(".%i",  ((ip->IP_Srcaddr&0x0000FF00)>>8 ));
                            DEBUG(".%i",  ((ip->IP_Srcaddr&0x00FF0000)>>16));
                            DEBUG(".%i :",((ip->IP_Srcaddr&0xFF000000)>>24));
                            break;
                    }
                    return;
                }
                else
                {
                    if( ip->IP_Proto == PROT_TCP ) tcp_socket_process();
                    if( ip->IP_Proto == PROT_UDP ) udp_socket_process();
                }
            }
            else
            if (ip->IP_Destaddr == (unsigned long)0xffffffff ) // if broadcast
Ejemplo n.º 3
0
static void service_arp_queue(struct netpoll_info *npi)
{
	struct sk_buff *skb;

	if (unlikely(!npi))
		return;

	skb = skb_dequeue(&npi->arp_tx);

	while (skb != NULL) {
		arp_reply(skb);
		skb = skb_dequeue(&npi->arp_tx);
	}
}
Ejemplo n.º 4
0
void rq_process(struct in_addr ipaddr, int ifindex) 
{
    RQ_ENTRY *cur_entry;
    RQ_ENTRY *prev_entry = NULL;

    pthread_mutex_lock(&arptab_mutex);
    parseproc();
    processarp(0);
    pthread_mutex_unlock(&arptab_mutex);

    pthread_mutex_lock(&req_queue_mutex);

    cur_entry = req_queue;
    
    /* Walk through the list */
    
    while (cur_entry != NULL) {
	if ( ipaddr.s_addr == *((long *) cur_entry->req_frame.arp.arp_tpa) && ifindex != cur_entry->req_if.sll_ifindex ) {

	    if (debug)
	        printf("Found %s in request queue\n", inet_ntoa(ipaddr));
	    arp_reply(&cur_entry->req_frame, &cur_entry->req_if);

	    /* Delete entry from the linked list */
	    	    
	    if (cur_entry == req_queue_tail)
		req_queue_tail = prev_entry;
	    
	    if (prev_entry != NULL)
		prev_entry->next = cur_entry->next;
	    else
		req_queue = cur_entry->next;
		
	    free(cur_entry);
	    cur_entry = prev_entry;
	
	    req_queue_len--;

	}

	if (cur_entry != NULL) {
    	    prev_entry = cur_entry;
	    cur_entry = cur_entry->next;
	}
    }
    
    pthread_mutex_unlock(&req_queue_mutex);
}
Ejemplo n.º 5
0
//----------------------------------------------------------------------------
//Check Packet and call Stack for TCP or UDP
void check_packet (void)
{
	//Pointer auf Ethernet_Header
	struct Ethernet_Header *ethernet;
	ethernet = (struct Ethernet_Header *)&eth_buffer[ETHER_OFFSET];

	//Pointer auf IP_Header
	struct IP_Header *ip;
	ip = (struct IP_Header *)&eth_buffer[IP_OFFSET];
#if USE_PING
	//Pointer auf ICMP_Header
	struct ICMP_Header *icmp;
	icmp = (struct ICMP_Header *)&eth_buffer[ICMP_OFFSET];
#endif

	if(ETHERNET_ARP_DATAGRAMM) {
		//Erzeugt ein ARP Reply Packet
		arp_reply();
	} else {
		if(ETHERNET_IP_DATAGRAMM && IF_MYIP) {
			arp_entry_add();			//Refresh des ARP Eintrages
#if USE_PING
			//Ist protokoll Byte = 1 dann ist es ein ICMP Packet
			if(IP_ICMP_PACKET) {
				switch ( icmp->ICMP_Type ) {
				case (0x08):
					//Echo-Request empfangen, erzeugen eines ICMP Reply Packet (PING Echo)
					icmp_send(ip->IP_Srcaddr,0x00,0x00,icmp->ICMP_SeqNum,icmp->ICMP_Id);
					break;
				case (0x00):
					//Echo-Reply Packet empfangen, Empfang melden
					//TODO: Erst Sequenznummer vergleichen?, Zeitmessung?
					DEBUG_WRITE("%i",(ip->IP_Srcaddr&0x000000FF));
					DEBUG_WRITE(".%i",((ip->IP_Srcaddr&0x0000FF00)>>8));
					DEBUG_WRITE(".%i",((ip->IP_Srcaddr&0x00FF0000)>>16));
					DEBUG_WRITE(".%i",((ip->IP_Srcaddr&0xFF000000)>>24));
					DEBUG_WRITE(": PONG!\r\n");
					break;
				}
				return;
			}
			else
#endif
			{
				if(IP_UDP_PACKET) udp_socket_process();
			}
		}
Ejemplo n.º 6
0
Archivo: arp.c Proyecto: rcacho/book
/*
 * Returns 0 if this is the packet we're waiting for
 * else -1 (and errno == 0)
 */
int
arprecv(struct nbuf *nbuf)

{
	int n = nbuf->len;
	struct ether_arp *ah = nbuf->nh.arph;


	errno = 0;	/* XXX */
	if (n < 0 || n < sizeof(struct ether_arp)) {
		return (-1);
	}


	/* Ethernet address now checked in readether() */

	if (ah->arp_hrd != htons(ARPHRD_ETHER) ||
	    ah->arp_pro != htons(ETHERTYPE_IP) ||
	    ah->arp_hln != sizeof(ah->arp_sha) ||
	    ah->arp_pln != sizeof(ah->arp_spa) )
	{
		return (-1);
	}

	if (ah->arp_op == htons(ARPOP_REQUEST)) {
		arp_reply(nbuf);
		return (-1);
	}

	if (ah->arp_op != htons(ARPOP_REPLY)) {
		return (-1);
	}

	/* Is the reply from the source we want? */
	if (bcmp(&arp_list[arp_num].addr,
			 ah->arp_spa, sizeof(ah->arp_spa)))
	{
		return (-1);
	}

	/* We don't care who the reply was sent to. */

	/* We have our answer. */

	return (0);
}
Ejemplo n.º 7
0
/*
 * Receive a UDP packet and validate it is for us.
 * Caller leaves room for the headers (Ether, IP, UDP)
 */
ssize_t
readudp(struct iodesc *d, void *pkt, size_t len, time_t tleft)
{
	ssize_t n;
	size_t hlen;
	struct ip *ip;
	struct udphdr *uh;
	struct udpiphdr *ui;
	struct ip tip;
	u_int16_t etype;	/* host order */

#ifdef NET_DEBUG
	if (debug)
		printf("readudp: called\n");
#endif

	uh = (struct udphdr *)pkt - 1;
	ip = (struct ip *)uh - 1;

	n = readether(d, ip, len + sizeof(*ip) + sizeof(*uh), tleft, &etype);
	if (n < 0 || (size_t)n < sizeof(*ip) + sizeof(*uh))
		return -1;

	/* Ethernet address checks now in readether() */

	/* Need to respond to ARP requests. */
	if (etype == ETHERTYPE_ARP) {
		struct arphdr *ah = (void *)ip;
		if (ah->ar_op == htons(ARPOP_REQUEST)) {
			/* Send ARP reply */
			arp_reply(d, ah);
		}
		return -1;
	}

	if (etype != ETHERTYPE_IP) {
#ifdef NET_DEBUG
		if (debug)
			printf("readudp: not IP. ether_type=%x\n", etype);
#endif
		return -1;
	}

	/* Check ip header */
	if (ip->ip_v != IPVERSION ||
	    ip->ip_p != IPPROTO_UDP) {	/* half char */
#ifdef NET_DEBUG
		if (debug)
			printf("readudp: IP version or not UDP. ip_v=%d ip_p=%d\n", ip->ip_v, ip->ip_p);
#endif
		return -1;
	}

	hlen = ip->ip_hl << 2;
	if (hlen < sizeof(*ip) ||
	    in_cksum(ip, hlen) != 0) {
#ifdef NET_DEBUG
		if (debug)
			printf("readudp: short hdr or bad cksum.\n");
#endif
		return -1;
	}
	NTOHS(ip->ip_len);
	if (n < ip->ip_len) {
#ifdef NET_DEBUG
		if (debug)
			printf("readudp: bad length %d < %d.\n", n, ip->ip_len);
#endif
		return -1;
	}
	if (d->myip.s_addr && ip->ip_dst.s_addr != d->myip.s_addr) {
#ifdef NET_DEBUG
		if (debug) {
			printf("readudp: bad saddr %s != ", inet_ntoa(d->myip));
			printf("%s\n", inet_ntoa(ip->ip_dst));
		}
#endif
		return -1;
	}

	/* If there were ip options, make them go away */
	if (hlen != sizeof(*ip)) {
		bcopy(((u_char *)ip) + hlen, uh, len - hlen);
		ip->ip_len = sizeof(*ip);
		n -= hlen - sizeof(*ip);
	}
	if (uh->uh_dport != d->myport) {
#ifdef NET_DEBUG
		if (debug)
			printf("readudp: bad dport %d != %d\n",
				d->myport, ntohs(uh->uh_dport));
#endif
		return -1;
	}

	if (uh->uh_sum) {
		n = ntohs(uh->uh_ulen) + sizeof(*ip);
		if (n > RECV_SIZE - ETHER_SIZE) {
			printf("readudp: huge packet, udp len %ld\n", (long)n);
			return -1;
		}

		/* Check checksum (must save and restore ip header) */
		tip = *ip;
		ui = (struct udpiphdr *)ip;
		bzero(ui->ui_x1, sizeof(ui->ui_x1));
		ui->ui_len = uh->uh_ulen;
		if (in_cksum(ui, n) != 0) {
#ifdef NET_DEBUG
			if (debug)
				printf("readudp: bad cksum\n");
#endif
			*ip = tip;
			return -1;
		}
		*ip = tip;
	}
	NTOHS(uh->uh_dport);
	NTOHS(uh->uh_sport);
	NTOHS(uh->uh_ulen);
	if (uh->uh_ulen < sizeof(*uh)) {
#ifdef NET_DEBUG
		if (debug)
			printf("readudp: bad udp len %d < %d\n",
				uh->uh_ulen, sizeof(*uh));
#endif
		return -1;
	}

	n -= sizeof(*ip) + sizeof(*uh);
	return (n);
}
Ejemplo n.º 8
0
int process_rx_packet(uint8_t *pu8Packet, uint32_t u32Len)
{
    ARP_PACKET    *arp = (ARP_PACKET *)pu8Packet;
    IP_PACKET    *ip  = (IP_PACKET *)pu8Packet;
    UDP_PACKET    *udp  = (UDP_PACKET *)pu8Packet;

    if (pu8Packet[0] == 0xFF) {     /* this is a broadcast packet */
        /*
         *  We manage the ARP reply process here.
         *  In the following code, if we have received a ARP request,
         *  we send ARP reply immediately.
         */
        if ((!COMPARE_IP(arp->au8TargetIP, g_au8IpAddr)) &&
                (arp->u16Type == SWAP16(PROTOCOL_ARP)) && (arp->u16Operation == SWAP16(ARP_REQUEST))) {
            arp_reply(arp->su8SenderIP, arp->au8SenderHA);
        }

        return 0;
    } else {                    /* this is a multicast or unicast packet */
        /*
         *  This is a unicast packet to us.
         */
        if ((ip->u8Prot == IP_PRO_TCP) && (!COMPARE_IP(ip->au8DestIP, g_au8IpAddr))) {
            // write me: process TCP packets here
            return 0;
        }

        if ((ip->u8Prot == IP_PRO_UDP) && (udp->u16SrcPort == SWAP16(67))) {
            // This is a DHCP packet...

            s_u32PktRdy = u32Len;
            memcpy(au8RxBuf, pu8Packet, u32Len);
            return 0;
        }

        if ((ip->u8Prot == IP_PRO_UDP) && (!COMPARE_IP(ip->au8DestIP, g_au8IpAddr))) {
            // write me: process UDP packets here
            return 0;
        }

        /*
         * Check ICMP Echo Request packet -
         * if matched, we reply it right here
         */
        if ((ip->u8Prot == IP_PRO_ICMP) && (!COMPARE_IP(ip->au8DestIP, g_au8IpAddr)) &&
                (pu8Packet[34] == 0x08)) {
            IP_PACKET    *tx_ip;


            /* duplicate packet then modify it */
            memcpy((char *)&au8TxBuf[0], (char *)&pu8Packet[0], u32Len);


            tx_ip = (IP_PACKET *)&au8TxBuf[0];
            memcpy((char *)tx_ip->au8DestMac, (char *)ip->au8SrcMac, 6);
            memcpy((char *)tx_ip->au8SrcMac, (char *)g_au8MacAddr, 6);
            tx_ip->u16Type = SWAP16(PROTOCOL_IP);
            tx_ip->u8VerHLen = 0x45;         /* fixed value, do not change it */
            tx_ip->u8ToS = 0;                /* no special priority */
            tx_ip->u16TLen = SWAP16(60);
            tx_ip->u16ID = SWAP16(s_u16IpPacketId);
            tx_ip->u16Frag = 0;
            tx_ip->u8TTL = 64;
            tx_ip->u8Prot = IP_PRO_ICMP;
            tx_ip->u16HdrChksum = 0;
            memcpy((char *)tx_ip->au8SrcIP, (char *)g_au8IpAddr, 4);
            memcpy((char *)tx_ip->au8DestIP, (char *)ip->au8SrcIP, 4);
            tx_ip->u16HdrChksum = ~chksum((uint16_t *)&tx_ip->u8VerHLen, 10);  /* 20 bytes */

            s_u16IpPacketId++;

            /* ICMP reply */
            au8TxBuf[34] = 0;

            /* ICMP checksum */
            au8TxBuf[36] = 0;
            au8TxBuf[37] = 0;
            *(uint16_t *)&au8TxBuf[36] = ~chksum((uint16_t *)&au8TxBuf[34], (u32Len - 34) / 2);

            EMAC_SendPkt(au8TxBuf, u32Len);

            return 0;
        }
    }

    return 0;
}
Ejemplo n.º 9
0
/*
 * reads an IP packet
 * WARNING: the old version stripped the IP options, if there were
 * any. Because we have absolutely no idea if the upper layer needs
 * these or not, it's best to leave them there.
 *
 * The size returned is the size indicated in the header.
 */
ssize_t
readip(struct iodesc * d, void *pkt, size_t len, time_t tleft, u_int8_t proto)
{
	ssize_t n;
	size_t hlen;
	struct ip *ip;
	u_int16_t etype;

	ip = (struct ip *) pkt - 1;

	n = readether(d, ip, len + sizeof(*ip), tleft, &etype);
	if (n == -1 || (size_t) n < sizeof(*ip))
		return -1;

	if (etype == ETHERTYPE_ARP) {
		struct arphdr *ah = (void *) ip;
		if (ah->ar_op == htons(ARPOP_REQUEST)) {
			/* Send ARP reply */
			arp_reply(d, ah);
		}
		return -1;
	}

	if (etype != ETHERTYPE_IP) {
#ifdef NET_DEBUG
		if (debug)
			printf("readip: not IP. ether_type=%x\n", etype);
#endif
		return -1;
	}

	/* Check ip header */
	if (ip->ip_v != IPVERSION ||
	    ip->ip_p != proto) { /* half char */
#ifdef NET_DEBUG
		if (debug) {
			printf("readip: wrong IP version or wrong proto "
			        "ip_v=%d ip_p=%d\n", ip->ip_v, ip->ip_p);
		}
#endif
		return -1;
	}

	hlen = ip->ip_hl << 2;
	if (hlen < sizeof(*ip) || ip_cksum(ip, hlen) != 0) {
#ifdef NET_DEBUG
		if (debug)
			printf("readip: short hdr or bad cksum.\n");
#endif
		return -1;
	}
	if (n < ntohs(ip->ip_len)) {
#ifdef NET_DEBUG
		if (debug)
			printf("readip: bad length %d < %d.\n",
			       (int) n, ntohs(ip->ip_len));
#endif
		return -1;
	}
	if (d->myip.s_addr && ip->ip_dst.s_addr != d->myip.s_addr) {
#ifdef NET_DEBUG
		if (debug) {
			printf("readip: bad saddr %s != ", inet_ntoa(d->myip));
			printf("%s\n", inet_ntoa(ip->ip_dst));
		}
#endif
		return -1;
	}
	return (ntohs(ip->ip_len) - 20);
}
Ejemplo n.º 10
0
void incoming_arp(VCC *vcc,struct atmarphdr *hdr,int len)
{
    ITF *itf;
    ENTRY *entry;
    void *sha,*ssa,*spa,*tha,*tsa,*tpa;
    struct sockaddr_atmsvc source,target;
    uint32_t src_ip,tgt_ip;
    unsigned char *here;

    if (len < hdr->data-(unsigned char *) hdr) {
	diag(COMPONENT,DIAG_ERROR,"got truncated ARP packet (%d bytes)",len);
	return;
    }
    if (hdr->ar_hrd != htons(ARPHRD_ATM)) {
	diag(COMPONENT,DIAG_ERROR,"unknown hw protocol 0x%04x",
	  ntohs(hdr->ar_hrd));
	return;
    }
    if (hdr->ar_pro != htons(ETH_P_IP)) {
	diag(COMPONENT,DIAG_ERROR,"unknown upper protocol 0x%04x",
	  ntohs(hdr->ar_pro));
	return;
    }
    if (!(hdr->ar_shtl & TL_LEN)) hdr->ar_shtl = 0; /* paranoia */
    if (!(hdr->ar_thtl & TL_LEN)) hdr->ar_thtl = 0;
    here = hdr->data;
    sha = get_addr(&here,hdr->ar_shtl & TL_LEN);
    ssa = get_addr(&here,hdr->ar_sstl & TL_LEN);
    spa = get_addr(&here,hdr->ar_spln);
    tha = get_addr(&here,hdr->ar_thtl & TL_LEN);
    tsa = get_addr(&here,hdr->ar_tstl & TL_LEN);
    tpa = get_addr(&here,hdr->ar_tpln);
    if (here-(unsigned char *) hdr > len) {
	diag(COMPONENT,DIAG_ERROR,"message too short (got %d, need %d)",len,
	  here-(unsigned char *) hdr);
	return;
    }
    set_addr(&source,sha,ssa,hdr->ar_shtl,hdr->ar_sstl);
    set_addr(&target,tha,tsa,hdr->ar_thtl,hdr->ar_tstl);
    src_ip = get_ip(spa);
    tgt_ip = get_ip(tpa);
{
   unsigned char *ipp;
   char buffer[MAX_ATM_ADDR_LEN+1];

   ipp = (unsigned char *) &src_ip;
   diag(COMPONENT,DIAG_DEBUG,"  SRC IP: %d.%d.%d.%d",ipp[0],ipp[1],ipp[2],
     ipp[3]);
   if (atm2text(buffer,MAX_ATM_ADDR_LEN+1,(struct sockaddr *) &source,pretty)
     >= 0) diag(COMPONENT,DIAG_DEBUG,"  SRC ATM: %s",buffer);
   ipp = (unsigned char *) &tgt_ip;
   diag(COMPONENT,DIAG_DEBUG,"  DST IP: %d.%d.%d.%d",ipp[0],ipp[1],ipp[2],
     ipp[3]);
   if (atm2text(buffer,MAX_ATM_ADDR_LEN+1,(struct sockaddr *) &target,pretty)
     >= 0) diag(COMPONENT,DIAG_DEBUG,"  DST ATM: %s",buffer);
}
    switch (ntohs(hdr->ar_op)) {
	case ARPOP_REQUEST:
	    diag(COMPONENT,DIAG_DEBUG,"got ARP_REQ");
	    if (learn(vcc,src_ip,&source)) break;
	    entry = NULL;
	    itf = lookup_itf_by_ip(tgt_ip);
	    entry = itf ? lookup_ip(itf,tgt_ip) : NULL;
	    if (entry && entry->state == as_valid && (entry->flags & ATF_PUBL))
	      {
		if (entry->addr)
		    arp_reply(vcc,tgt_ip,entry->addr,src_ip,&source);
		else arp_nak(vcc,tgt_ip,src_ip,&source);
	    }
	    else {
		if (itf && itf->local_ip == tgt_ip)
		    arp_reply(vcc,tgt_ip,NULL,src_ip,&source);
		else arp_nak(vcc,tgt_ip,src_ip,&source);
	    }
	    break;
	case ARPOP_REPLY:
	    diag(COMPONENT,DIAG_DEBUG,"got ARP_REP");
	    if (!vcc->entry || !(vcc->entry->flags & ATF_ARPSRV)) {
		diag(COMPONENT,DIAG_ERROR,"got ARP response from charlatan");
		break;
	    }
	    (void) learn(NULL,src_ip,&source);
	    break;
	case ARPOP_InREQUEST:
	    diag(COMPONENT,DIAG_DEBUG,"got InARP_REQ");
	    if (!learn(vcc,src_ip,&source)) inarp_reply(vcc,src_ip,&source);
	    break;
	case ARPOP_InREPLY:
	    diag(COMPONENT,DIAG_DEBUG,"got InARP_REP");
	    (void) learn(vcc,src_ip,&source);
	    break;
	case ARPOP_NAK:
	    diag(COMPONENT,DIAG_DEBUG,"got ARP_NAK");
	    if (!vcc->entry || !(vcc->entry->flags & ATF_ARPSRV)) {
		diag(COMPONENT,DIAG_ERROR,"got ARP response from charlatan");
		break;
	    }
	    learn_nak(tgt_ip);
	    break;
	default:
	    diag(COMPONENT,DIAG_ERROR,"unrecognized ARP op 0x%x",
	      ntohs(hdr->ar_op));
    }
}
Ejemplo n.º 11
0
//----------------------------------------------------------------------------
//ETH get data
void eth_get_data (void)
{ 	
	if(eth.timer)
	{
		tcp_timer_call();
		arp_timer_call();
		eth.timer = 0;
	}	
	if(eth.data_present)
	{
	#if USE_ENC28J60
		while(ETH_INT_ACTIVE)
		{	
	#endif

	#if USE_RTL8019
		if ( (ReadRTL(RTL_ISR)&(1<<OVW)) != 0)
			{
			DEBUG ("Overrun!\n");
			}

		if ( (ReadRTL(RTL_ISR) & (1<<PRX)) != 0)
		{
			unsigned char ByteH = 0;
			unsigned char ByteL = 1;
		
			while (ByteL != ByteH) //(!= bedeutet ungleich)
			{	
	#endif	
				unsigned int packet_length;
				  
				packet_length = ETH_PACKET_RECEIVE(MTU_SIZE,eth_buffer);
				if(packet_length > 0)
				{
					eth_buffer[packet_length+1] = 0;
					check_packet();
				}
			
	#if USE_RTL8019
				//auslesen des Empfangsbuffer BNRY = CURR
				ByteL = ReadRTL(BNRY); //auslesen NIC Register bnry
				WriteRTL ( CR ,(1<<STA|1<<RD2|1<<PS0));
			
				ByteH = ReadRTL(CURR); //auslesen NIC Register curr
				WriteRTL ( CR ,(1<<STA|1<<RD2));
			}
	#endif
		}
	#if USE_RTL8019
		Networkcard_INT_RES();
		Networkcard_Start();
	#endif
		eth.data_present = 0;
		ETH_INT_ENABLE;
	}
	return;
}
//----------------------------------------------------------------------------
//Check Packet and call Stack for TCP or UDP
void check_packet (void)
{
    struct Ethernet_Header *ethernet;    //Pointer auf Ethernet_Header
    struct IP_Header       *ip;          //Pointer auf IP_Header
    struct TCP_Header      *tcp;         //Pointer auf TCP_Header
    struct ICMP_Header     *icmp;        //Pointer auf ICMP_Header

    ethernet = (struct Ethernet_Header *)&eth_buffer[ETHER_OFFSET];
    ip       = (struct IP_Header       *)&eth_buffer[IP_OFFSET];
    tcp      = (struct TCP_Header      *)&eth_buffer[TCP_OFFSET];
    icmp     = (struct ICMP_Header     *)&eth_buffer[ICMP_OFFSET];
    
    if(ethernet->EnetPacketType == HTONS(0x0806) )     //ARP
    {
        arp_reply(); // check arp packet request/reply
    }
    else
    {
        if( ethernet->EnetPacketType == HTONS(0x0800) )  // if IP
        {              
            if( ip->IP_Destaddr == *((unsigned long*)&myip[0]) )  // if my IP address 
            {
                arp_entry_add();  ///Refresh des ARP Eintrages
                if(ip->IP_Proto == PROT_ICMP)
                {
                    switch ( icmp->ICMP_Type )
                    {
                        case (8): //Ping reqest
                            icmp_send(ip->IP_Srcaddr,0,0,icmp->ICMP_SeqNum,icmp->ICMP_Id); 
                            break;
                            
                        case (0): //Ping reply
                            if ((*((unsigned long*)&ping.ip1[0])) == ip->IP_Srcaddr)
                            {
                                ping.result |= 0x01;
                            }
                            DEBUG("%i",    (ip->IP_Srcaddr&0x000000FF)     );
                            DEBUG(".%i",  ((ip->IP_Srcaddr&0x0000FF00)>>8 ));
                            DEBUG(".%i",  ((ip->IP_Srcaddr&0x00FF0000)>>16));
                            DEBUG(".%i :",((ip->IP_Srcaddr&0xFF000000)>>24));
                            break;
                    }
                    return;
                }
                else
                {
                    if( ip->IP_Proto == PROT_TCP ) tcp_socket_process();
                    if( ip->IP_Proto == PROT_UDP ) udp_socket_process();
                }
            }
            else
            if (ip->IP_Destaddr == (unsigned long)0xffffffff || ip->IP_Destaddr == *((unsigned long*)&broadcast_ip[0]) ) // if broadcast
            {
                if( ip->IP_Proto == PROT_UDP ) udp_socket_process();
            }
        }
Ejemplo n.º 12
0
/*
 * Returns 0 if this is the packet we're waiting for
 * else -1 (and errno == 0)
 */
static ssize_t
arprecv(struct iodesc *d, void **pkt, void **payload, time_t tleft, void *extra)
{
	ssize_t n;
	struct ether_arp *ah;
	uint16_t etype;	/* host order */
	void *ptr;

#ifdef ARP_DEBUG
	if (debug)
		printf("arprecv: ");
#endif

	ptr = NULL;
	n = readether(d, &ptr, (void **)&ah, tleft, &etype);
	errno = 0;	/* XXX */
	if (n == -1 || n < sizeof (struct ether_arp)) {
#ifdef ARP_DEBUG
		if (debug)
			printf("bad len=%d\n", n);
#endif
		free(ptr);
		return (-1);
	}

	if (etype != ETHERTYPE_ARP) {
#ifdef ARP_DEBUG
		if (debug)
			printf("not arp type=%d\n", etype);
#endif
		free(ptr);
		return (-1);
	}

	/* Ethernet address now checked in readether() */
	if (ah->arp_hrd != htons(ARPHRD_ETHER) ||
	    ah->arp_pro != htons(ETHERTYPE_IP) ||
	    ah->arp_hln != sizeof (ah->arp_sha) ||
	    ah->arp_pln != sizeof (ah->arp_spa)) {
#ifdef ARP_DEBUG
		if (debug)
			printf("bad hrd/pro/hln/pln\n");
#endif
		free(ptr);
		return (-1);
	}

	if (ah->arp_op == htons(ARPOP_REQUEST)) {
#ifdef ARP_DEBUG
		if (debug)
			printf("is request\n");
#endif
		arp_reply(d, ah);
		free(ptr);
		return (-1);
	}

	if (ah->arp_op != htons(ARPOP_REPLY)) {
#ifdef ARP_DEBUG
		if (debug)
			printf("not ARP reply\n");
#endif
		free(ptr);
		return (-1);
	}

	/* Is the reply from the source we want? */
	if (bcmp(&arp_list[arp_num].addr, ah->arp_spa, sizeof (ah->arp_spa))) {
#ifdef ARP_DEBUG
		if (debug)
			printf("unwanted address\n");
#endif
		free(ptr);
		return (-1);
	}
	/* We don't care who the reply was sent to. */

	/* We have our answer. */
#ifdef ARP_DEBUG
	if (debug)
		printf("got it\n");
#endif
	*pkt = ptr;
	*payload = ah;
	return (n);
}