Exemplo n.º 1
0
PACKET
pk_prepend(PACKET pkt, int bigger)
{
   PACKET newpkt;

   LOCK_NET_RESOURCE(FREEQ_RESID);
   newpkt = pk_alloc(bigger);
   UNLOCK_NET_RESOURCE(FREEQ_RESID);
   if(!newpkt)
   {
      LOCK_NET_RESOURCE(FREEQ_RESID);
      pk_free(pkt);
      UNLOCK_NET_RESOURCE(FREEQ_RESID);
      return NULL;
   }
   newpkt->nb_prot = newpkt->nb_buff;  /* no MAC prepend */

   /* set lengths of this buffer - no data yet */
   newpkt->nb_plen = 0;       /* nothing in this buffer */
   newpkt->nb_tlen = pkt->nb_tlen;  /* total chain length unchanged */

   newpkt->pk_next = pkt;
   newpkt->pk_prev = NULL;
   /* ensure that the newly allocated buffer's PKF_HEAPBUF and 
    * PKF_INTRUNSAFE flags aren't overwritten */
   newpkt->flags |= (pkt->flags & (~(PKF_HEAPBUF | PKF_INTRUNSAFE)));
   newpkt->net = pkt->net;
   pkt->pk_prev = newpkt;     /* link new pkt */
   return(newpkt);
}
Exemplo n.º 2
0
int dump_hbuf_stats (void * pio)
{
   u_long hb_local [HBUF_NUM_STATS];
   u_long heap_curr_mem_local;
   u_long heap_curr_mem_hi_watermark_local;
#ifdef HEAPBUFS_DEBUG
   PHLEP phlep;
   u_short count = 0;
   u_long max_alloc = 0;
   u_long min_alloc = 0xFFFFFFFF;
   u_long total_alloc = 0;
#endif

   LOCK_NET_RESOURCE(FREEQ_RESID);

   ENTER_CRIT_SECTION(&hbufstats);
   MEMCPY (&hb_local, &hbufstats, sizeof(hbufstats));
   EXIT_CRIT_SECTION(&hbufstats);
   
   ENTER_CRIT_SECTION(&heap_curr_mem);
   heap_curr_mem_local = heap_curr_mem;
   heap_curr_mem_hi_watermark_local = heap_curr_mem_hi_watermark;
   EXIT_CRIT_SECTION(&heap_curr_mem);

   UNLOCK_NET_RESOURCE(FREEQ_RESID);

   ns_printf(pio, "Heap buffer error and other statistics:\n");
   ns_printf(pio, "Current total allocation %lu, high watermark %lu\n",heap_curr_mem_local,heap_curr_mem_hi_watermark_local);
   ns_printf(pio, "Successful allocations %lu, size netbuf %u, size PHLE %u\n",hb_local[HB_ALLOC_SUCC],sizeof(struct netbuf),sizeof(PHLE));
   ns_printf(pio, "Bad request size failures %lu, Max heap allocation exceeded failures %lu\n",hb_local[TOOBIG_ALLOC_ERR],hb_local[LIMIT_EXCEEDED_ERR]);
   ns_printf(pio, "netbuf allocation failures %lu, data buffer allocation failures %lu\n",hb_local[NB_ALLOCFAIL_ERR],hb_local[DB_ALLOCFAIL_ERR]);
   ns_printf(pio, "Inconsistent fields %lu, Guard band violations %lu\n",hb_local[INCONSISTENT_HBUF_LEN_ERR],hb_local[HB_GUARD_BAND_VIOLATED_ERR]);
#ifdef HEAPBUFS_DEBUG
   ns_printf(pio, "Private heapbuf list element allocation failures %lu, missing private heapbuf list element entry %lu\n",hb_local[PHLEB_ALLOCFAIL_ERR],hb_local[NO_PHLE_ERR]);
   
   LOCK_NET_RESOURCE(FREEQ_RESID);
   ENTER_CRIT_SECTION(&phlq);
   for (phlep=(PHLEP)phlq.q_head; phlep; phlep = phlep->next)
   {
      if (max_alloc < phlep->length) max_alloc = phlep->length;
      if (min_alloc > phlep->length) min_alloc = phlep->length;

      total_alloc += phlep->length;
      ++count; 
   }
   EXIT_CRIT_SECTION(&phlq);
   UNLOCK_NET_RESOURCE(FREEQ_RESID);

   if (count == 0)
      ns_printf (pio, "No heap buffers currently allocated\n");
   else
      ns_printf(pio, "Number of heap buffers currently allocated %lu, min length %lu, max length %lu, total allocation %lu\n", \
       count, min_alloc, max_alloc, total_alloc);
#endif /* HEAPBUFS_DEBUG */

   return 0;
}
Exemplo n.º 3
0
struct mbuf *  
m_getnbuf(int type, int len)
{
   struct mbuf *  m;
   PACKET pkt = NULL;

#ifdef NPDEBUG
   if (type < MT_RXDATA || type > MT_IFADDR)
   {
      dtrap(); /* is this OK? */
   }
#endif

   /* if caller has data (len >= 0), we need to allocate 
    * a packet buffer; else all we need is the mbuf */
   if (len != 0)
   {
      LOCK_NET_RESOURCE(FREEQ_RESID);
      pkt = pk_alloc(len + HDRSLEN);

      UNLOCK_NET_RESOURCE(FREEQ_RESID);
      if (!pkt)
         return NULL;
   }

   m = (struct mbuf *)getq(&mfreeq);
   if (!m)
   {
      if (pkt) 
      {
         LOCK_NET_RESOURCE(FREEQ_RESID);
         pk_free(pkt);
         UNLOCK_NET_RESOURCE(FREEQ_RESID);
      }
      return NULL;
   }
   m->m_type = type;
   if (len == 0)
   {
      m->pkt = NULL;
      m->m_base = NULL;    /* caller better fill these in! */
      m->m_memsz = 0;
   }
   else
   {
      m->pkt = pkt;
      /* set m_data to the part where tcp data should go */
      m->m_base = m->m_data = pkt->nb_prot = pkt->nb_buff + HDRSLEN;
      m->m_memsz = pkt->nb_blen - HDRSLEN;
   }
   m->m_len = 0;
   m->m_next = m->m_act = NULL;
   mbstat.allocs++;        /* maintain local statistics */
   putq(&mbufq, (qp)m);
   return m;
}
Exemplo n.º 4
0
int
tcp_rcv(PACKET pkt)     /* NOTE: pkt has nb_prot pointing to IP header */
{
   struct mbuf *  m_in;
   struct ip * bip;  /* IP header, berkeley version */
   struct tcphdr *   tcpp;
   unshort  len;  /* scratch length holder */

   /* For TCP, the netport IP layer is modified to set nb_prot to the 
    * start of the IP header (not TCP). We need to do some further
    * mods which the BSD code expects:
    */
   bip = (struct ip *)pkt->nb_prot;    /* get ip header */
   len = ntohs(bip->ip_len);  /* get length in local endian */

   /* verify checksum of received packet */

   tcpp = (struct tcphdr *)ip_data(bip);
   if (tcp_cksum(bip) != tcpp->th_sum)
   {
      TCP_MIB_INC(tcpInErrs);    /* keep MIB stats */
      tcpstat.tcps_rcvbadsum++;  /* keep BSD stats */
      LOCK_NET_RESOURCE(FREEQ_RESID);
      pk_free(pkt);  /* punt packet */
      UNLOCK_NET_RESOURCE(FREEQ_RESID);
      return ENP_BAD_HEADER;
   }

   m_in = m_getnbuf(MT_RXDATA, 0);
   if (!m_in){
      LOCK_NET_RESOURCE(FREEQ_RESID);
      pk_free(pkt);
      UNLOCK_NET_RESOURCE(FREEQ_RESID);
      return ENP_RESOURCE;  
   }

   IN_PROFILER(PF_TCP, PF_ENTRY);      /* measure time in TCP */

   /* subtract IP header length from total IP packet length */
   len -= ((unshort)(bip->ip_ver_ihl & 0x0f) << 2);
   bip->ip_len = len;   /* put TCP length in struct for TCP code to use */

   /* set mbuf to point to start of IP header (not TCP) */
   m_in->pkt = pkt;
   m_in->m_data = pkt->nb_prot;
   m_in->m_len = pkt->nb_plen;
   m_in->m_base = pkt->nb_buff;     /* ??? */
   m_in->m_memsz = pkt->nb_blen;    /* ??? */

   tcp_input(m_in, pkt->net);

   IN_PROFILER(PF_TCP, PF_EXIT);      /* measure time in TCP */

   return 0;
}
Exemplo n.º 5
0
int
t_errno(long s)
{
   struct socket *so = LONG2SO(s);
   struct socket *tmp;
   int errcode = ENOTSOCK;

   LOCK_NET_RESOURCE(NET_RESID);    /* protect soq */

   /* search socket queue for passed socket. This routine should
    * not use SOC_CHECK since it can be ifdeffed out, and we must
    * be ready to return EPIPE if the socket does not exist.
    */
   for (tmp = (struct socket *)(&soq); tmp; tmp = tmp->next)
   {
      if (tmp == so)  /* found socket, return error */
      {
         errcode = so->so_error;
         break;
      }
   }

   UNLOCK_NET_RESOURCE(NET_RESID);

   return errcode;
}
Exemplo n.º 6
0
void
ip_raw_free(PACKET p)
{
   LOCK_NET_RESOURCE(FREEQ_RESID);
   PK_FREE(p);
   UNLOCK_NET_RESOURCE(FREEQ_RESID);
}
Exemplo n.º 7
0
void
tcp_sleep(void * event)
{
   int   i;

   /* search event array for an unused slot */
   for (i = 0; i < MAX_EVENTS; i++)
   {
      if (tk_eventlist[i].event == 0)     /* found a slot */
      {
         tk_eventlist[i].event = event;   /* save event to wake up on */
         tk_eventlist[i].task = TK_THIS;  /* save calling task */
         UNLOCK_NET_RESOURCE(NET_RESID);  /* free stack mutex */
         TK_BLOCK();                      /* suspend calling task */
         LOCK_NET_RESOURCE(NET_RESID);    /* we woke up - reenter stack */
         tk_eventlist[i].event = NULL;    /* clear array entry */
         return;
      }
   }
   /* fall to here if we ran out of free event slots. Best thing to do is
    * let system spin, then return to caller for another sleep test.
    */
   tcp_no_taskslot++;
   tk_yield();
}
Exemplo n.º 8
0
void
rfsim_timer()
{
   ip_addr     hop;
   struct ip * pip;
   PACKET      pkt;

   /* send al packets which have timed out */
   while(((PACKET)(simq.q_head))->nb_tstamp < cticks)
   {
      pkt = (PACKET)getq(&simq); /* get pkt to send */
      hop = pkt->fhost;          /* get hop from host field */
      pip = ip_head(pkt);        /* get real host address */
      pkt->fhost = pip->ip_dest; /* restore host field */
      simpkts++;

      /* see if it's time to drop a packet */
      if((lossrate) && 
         ((simpkts - simlastloss) > lossrate) && 
         ((cticks & deviation) == 1))
      {
         LOCK_NET_RESOURCE(FREEQ_RESID);
         pk_free(pkt);           /* drop instead of send */
         UNLOCK_NET_RESOURCE(FREEQ_RESID);
         simlastloss = simpkts;  /* reset drop timer */
         simdrops++;             /* count drops */
      }
      else
         ip2mac(pkt, hop);          /* send pkt to hardware */
   }
   return;
}
Exemplo n.º 9
0
void
tcp_tick()
{
   /* guard against re-entry */
   if (in_tcptick)
      return;
   in_tcptick++;

   LOCK_NET_RESOURCE(NET_RESID);

   if (cticks >= nextslow) /* time to do it again */
   {
      tcp_slowtimo();      /* call routine in BSD tcp_timr.c */
#ifdef CSUM_DEMO
      nextslow = cticks + (TPS/5);  /* another 200 ms */
#else
      nextslow = cticks + (TPS/2);  /* another 500 ms */
#endif
   }

#ifdef DO_DELAY_ACKS
   tcp_fasttimo();
#endif   /* DO_DELAY_ACKS */

   UNLOCK_NET_RESOURCE(NET_RESID);

   in_tcptick--;
}
Exemplo n.º 10
0
int ftpc_send_msg4 (u_long type, 
                    u_long pio, 
                    u_char * arg1p, 
                    u_long arg1len,
                    u_char * arg2p, 
                    u_long arg2len,
                    u_char * arg3p, 
                    u_long arg3len)
{
   struct ftpctask_msg * msgp;
   unsigned char * startp;

   msgp = (struct ftpctask_msg *) FTPC_ALLOC (sizeof (struct ftpctask_msg) + arg1len + arg2len + arg3len);
   if (!msgp)
   {
      ++ftpc_err.alloc_fail;
      return -1;
   }
   
   msgp->type = type;
   msgp->pio = pio;
   startp = &(msgp->parms[0]);
   memcpy (startp, arg1p, arg1len);
   memcpy (startp + arg1len, arg2p, arg2len);
   memcpy (startp + arg1len + arg2len, arg3p, arg3len);

   /* send message to FTP client task */
   LOCK_NET_RESOURCE (FTPCQ_RESID);
   putq(&ftpcq, (q_elt)msgp);
   UNLOCK_NET_RESOURCE (FTPCQ_RESID);

   post_app_sem (FTPC_SEMID);

   return 0;
}
Exemplo n.º 11
0
int
t_getsockopt(long s,
   int   level,
   int   name,
   void *   arg,
   int   arglen)

{
   struct socket *   so;
   int   err;

   so = LONG2SO(s);
   SOC_CHECK(so);
   USE_ARG(level);
   USE_ARG(arglen);

   LOCK_NET_RESOURCE (NET_RESID);

   INET_TRACE (INETM_SOCKET,
    ("INET: getsockopt: name %x val %x valsize %d\n",
    name, val));

   /* is it a level IP_OPTIONS call? */
   if (level != IP_OPTIONS)
   {
      if ((err = sogetopt (so, name, arg)) != 0) 
      {
         so->so_error = err;
         UNLOCK_NET_RESOURCE (NET_RESID);
         return SOCKET_ERROR;
      }
   }
   else
   {
      /* level 1 options are for the IP packet level.
       * the info is carried in the socket CB, then put 
       * into the PACKET.
       */
      if (name == IP_TTL_OPT)
      {
         if (!so->so_optsPack) *(int *)arg = IP_TTL;
         else *(int *)arg = (int)so->so_optsPack->ip_ttl;
      }
      else if (name == IP_TOS)
      {
         if (!so->so_optsPack) *(int *)arg = IP_TOS_DEFVAL;
         else *(int *)arg = (int)so->so_optsPack->ip_tos;
      }
      else
      {
         UNLOCK_NET_RESOURCE (NET_RESID);
         return SOCKET_ERROR;
      }
   }   
   so->so_error = 0;

   UNLOCK_NET_RESOURCE (NET_RESID);
   return 0;
}
Exemplo n.º 12
0
BOOL GetNextTcpInfo(HTCPINFO* p_pHTcp, T_TCPINFO* p_pTcpInfo, TcpState p_nTcpState)
{
	if(p_pHTcp == NULL)
		return FALSE;

	struct socket *   tmpso = ((struct socket *)(*p_pHTcp))->next;
	*p_pHTcp = NULL;

	LOCK_NET_RESOURCE(NET_RESID);
	ENTER_CRIT_SECTION();
	//locknet_check(&soq);  /* make sure queue is protected */

	for(;tmpso != NULL;tmpso=tmpso->next)
	{
		if((tmpso->so_domain == AF_INET6) && (tmpso->so_type==SOCK_STREAM)) //just ipv6 tcp connections
		{
			if(p_nTcpState == TCP_STATE_LISTEN)
			{
				if (((struct tcpcb *)tmpso->so_pcb->inp_ppcb)->t_state == TCPS_LISTEN)
				{
					strcpy(p_pTcpInfo->pcLocalAddr,FormatHex((void*)tmpso->so_pcb->ip6_laddr.addr,IPV6_ADDR_LEN,-1));
					p_pTcpInfo->shLocalPort = ntohs(tmpso->so_pcb->inp_lport);

					strcpy(p_pTcpInfo->pcForeignAddr,FormatHex((void*)tmpso->so_pcb->ip6_faddr.addr,IPV6_ADDR_LEN,-1));
					p_pTcpInfo->shForeignPort= ntohs(tmpso->so_pcb->inp_fport);

					*p_pHTcp = tmpso;
					break;
				}
			}

			if(p_nTcpState == TCP_STATE_ACTIVE)
			{
				if (((struct tcpcb *)tmpso->so_pcb->inp_ppcb)->t_state == TCPS_ESTABLISHED)
				{
					strcpy(p_pTcpInfo->pcLocalAddr,FormatHex((void*)tmpso->so_pcb->ip6_laddr.addr,IPV6_ADDR_LEN,-1));
					p_pTcpInfo->shLocalPort = ntohs(tmpso->so_pcb->inp_lport);

					strcpy(p_pTcpInfo->pcForeignAddr,FormatHex((void*)tmpso->so_pcb->ip6_faddr.addr,IPV6_ADDR_LEN,-1));
					p_pTcpInfo->shForeignPort= ntohs(tmpso->so_pcb->inp_fport);

					*p_pHTcp = tmpso;
					break;
				}
			}
		}
	}

	//queue_check(&soq);         /* make sure queue is not corrupted */
	EXIT_CRIT_SECTION();   /* restore int state */
	UNLOCK_NET_RESOURCE(NET_RESID);

   if(*p_pHTcp == NULL)
	   return FALSE;

	return TRUE;
}
Exemplo n.º 13
0
PACKET
pk_gather(PACKET pkt, int headerlen)
{
   PACKET   newpkt;
   PACKET   tmppkt;
   int      oldlen, newlen;
   char *   cp;

   oldlen = pkt->nb_tlen;

   LOCK_NET_RESOURCE(FREEQ_RESID);
   newpkt = pk_alloc(oldlen + headerlen);
   UNLOCK_NET_RESOURCE(FREEQ_RESID);
   if(!newpkt)
      return NULL;

   newpkt->nb_prot = newpkt->nb_buff + headerlen;
   /* ensure that the newly allocated buffer's PKF_HEAPBUF and 
    * PKF_INTRUNSAFE flags aren't overwritten */
   newpkt->flags |= (pkt->flags & (~(PKF_HEAPBUF | PKF_INTRUNSAFE)));
   newpkt->net = pkt->net;
   newpkt->pk_prev = newpkt->pk_next = NULL;

   tmppkt = pkt;        /* save packet for pk_free call below */
   newlen = 0;
   cp = newpkt->nb_prot;
   while(pkt)
   {
      MEMCPY(cp, pkt->nb_prot, pkt->nb_plen);
      newlen += pkt->nb_plen;
      cp += pkt->nb_plen;  /* bump pointer to data */
      pkt = pkt->pk_next;  /* next packet in chain */
   }
   LOCK_NET_RESOURCE(FREEQ_RESID);
   pk_free(tmppkt);     /* free last packet in chain */
   UNLOCK_NET_RESOURCE(FREEQ_RESID);
   if(newlen != oldlen)    /* make sure length was right */
      panic("pk_gather");

   newpkt->nb_plen = newlen;
   return newpkt;
}
Exemplo n.º 14
0
int igmpv2_input (PACKET p)
{
   struct igmp * igmp;
   struct ip * pip;
   int igmplen;
   u_char type;
   int rc;

   pip = ip_head (p);    
   /* compute length of IGMP packet (after accounting for IP header, 
    * including the IP Router Alert option (if present)) */   
   igmplen = p->nb_plen - ip_hlen (pip);
   igmp = (struct igmp *) (ip_data (pip));   
   /* extract the IGMP packet type from received packet */
   type = igmp->igmp_type;

   switch (type) 
   {
      case IGMP_HOST_MEMBERSHIP_QUERY:
         rc = igmpv2_process_query (p);
         break;

      case IGMP_HOST_MEMBERSHIP_REPORT:
      case IGMPv2_MEMBERSHIP_REPORT:
         rc = igmpv2_process_report (p);
         break;
         
      case IGMPv2_LEAVE_GROUP:
         /* Leave messages are typically addressed to the all-routers 
          * multicast address group (224.0.0.2).  We do not implement 
          * multicast router functionality, and therefore, do not 
          * expect to receive such messages.  However, according to
          * RFC 2236, some implementations of an older version of the 
          * IGMPv2 specification send leave messages to the group 
          * being left.  If we do receive such a message, we will 
          * drop it. */       
         ++igmpstats.igmpv2mode_v2_leave_msgs_rcvd;
         rc = IGMP_OK;
         break;               

      default:     
         ++igmpstats.igmpv2mode_unknown_pkttype;
         rc = IGMP_ERR;         
         break;
   } /* end SWITCH */

   /* we're done processing the received packet; return packet buffer 
    * back to free pool */
   LOCK_NET_RESOURCE(FREEQ_RESID);
   pk_free(p);
   UNLOCK_NET_RESOURCE(FREEQ_RESID);
   
   return rc;
}
Exemplo n.º 15
0
/* FUNCTION: v1_checksock()
 * 
 * v1_checksock() - Check if any SNMP requests have been
 * received on the socket. If yes, process them, and send the response.
 *
 * PARAM1: SOCKTYPE           socket
 *
 * RETURN: none
 */
void
v1_checksock(SOCKTYPE sock)
{
   struct sockaddr sa;
   int sa_len = sizeof(struct sockaddr);
   int e;
   int len = 0;

   /* check for received snmp packet */
   if (sock != INVALID_SOCKET)
   {
      len = recvfrom(sock, (char *)inbuf, SNMPSIZ, 0, &sa, &sa_len);
      if (len < 0)
      {
         e = t_errno(sock);
         if (e != EWOULDBLOCK) /* no data received */
         {
            dprintf("snmp: socket read error %d\n", e);
         }
         return;
      }
      else if (len == 0)
      {
         dtrap(); /* socket closed? */
         return;
      }
      /* else (len > 0) */

      if (agent_on)              /* agent is active */
      {
         LOCK_NET_RESOURCE(SNMP_RESID);
         e = snmp_agt_parse(inbuf, len, snmpbuf, SNMPSIZ);
         if (e)                  /* parse worked, send response packet */
         {
            len = e;    /* e is length of snmp reply */
            if (sa.sa_family == AF_INET)
               sa_len = sizeof(struct sockaddr_in);
#ifdef IP_V6
            else
               sa_len = sizeof(struct sockaddr_in6);
#endif
            e = sendto(sock, (char *)snmpbuf, len, 0, &sa, sa_len);
            if (e != len)
            {
               e = t_errno(sock);
               dprintf("snmp: socket send error \n");
               dtrap();
            }
         }
         UNLOCK_NET_RESOURCE(SNMP_RESID);
      }
   }
}
Exemplo n.º 16
0
void
ping6_timer()
{
   struct ping6 *ping;
   struct ping6 *next;

   LOCK_NET_RESOURCE(NET_RESID); /* protect ping6q list */
   ping = ping6q;
   while (ping)
   {
      next = ping->next;

      /* see if session should be killed */
      if ((ping->sent - ping->replies) > MAX_MISSING_PINGS)
      {
         ping6_done(ping);
         ping = next;
         continue;
      }
      /* see if it's time to ping again or time to give up*/
      if (TIME_EXP(ping->nextping, CTICKS))
      {
         if (TIME_EXP(TIME_ADD(ping->last, ping->wait_time), CTICKS))
         {
            ping6_done(ping);  /* Too long since last received ping */
            ping = next;
            continue;
         }
         UNLOCK_NET_RESOURCE(NET_RESID);
         if (ping->sent < ping->count)
            ping6_send(ping);
         LOCK_NET_RESOURCE(NET_RESID); /* protect ping6q list */
      }
      ping = next;
   }
   UNLOCK_NET_RESOURCE(NET_RESID);
   return;
}
Exemplo n.º 17
0
int
t_recv (long s, 
   char *   buf,
   int   len, 
   int   flag)
{
#ifdef SOCKDEBUG
   char logbuf[10];
#endif
   struct socket *   so;
   int   err;
   int   sendlen = len;

   so = LONG2SO(s);
#ifdef SOC_CHECK_ALWAYS
   SOC_CHECK(so);
#endif
   if ((so->so_state & SO_IO_OK) != SS_ISCONNECTED)
   {
      so->so_error = EPIPE;
#ifdef SOCKDEBUG
      sprintf(logbuf, "t_recv: %d", so->so_error);
      glog_with_type(LOG_TYPE_DEBUG, logbuf, 1);
#endif
      return SOCKET_ERROR;
   }
   so->so_error = 0;

   LOCK_NET_RESOURCE(NET_RESID);
   IN_PROFILER(PF_TCP, PF_ENTRY);        /* measure time in TCP */
   INET_TRACE (INETM_IO, ("INET:recv: so %x, len %d\n", so, len));
   err = soreceive(so, NULL, buf, &len, flag);
   IN_PROFILER(PF_TCP, PF_EXIT);        /* measure time in TCP */
   UNLOCK_NET_RESOURCE(NET_RESID);

   if(err)
   {
      so->so_error = err;
#ifdef SOCKDEBUG
      sprintf(logbuf, "t_recv: %d", so->so_error);
      glog_with_type(LOG_TYPE_DEBUG, logbuf, 1);
#endif
      return SOCKET_ERROR;
   }

   /* return bytes we sent - the amount we wanted to send minus
    * the amount left in the buffer.
    */
   return (sendlen - len);
}
Exemplo n.º 18
0
int
ni_set_state(NET ifp, int opcode)
{
   int   err = 0;

   if ((opcode != NI_DOWN) &&
       (opcode != NI_UP))
   {
      return ENP_PARAM;
   }

   LOCK_NET_RESOURCE(NET_RESID);

   if (opcode == NI_DOWN)  /* clean up system tables */
   {
#ifdef INCLUDE_TCP
      if_killsocks(ifp);      /* kill this iface's sockets */
#endif   /* INCLUDE_TCP */
      del_route(0, 0, if_netnumber(ifp));    /* delete any IP routes */
      clear_arp_entries(NULLIP, ifp);        /* delete any ARP entries */
   }

   /* force if-mib AdminStatus flag to correct setting. This will
    * keep devices without n_setstate() calls from receiving any
    * packet to send from ip2mac().
    */
   if (opcode == NI_UP)
      ifp->n_mib->ifAdminStatus = NI_UP;
   else
      ifp->n_mib->ifAdminStatus = NI_DOWN;

   ifp->n_mib->ifLastChange = cticks * (100/TPS);
   if (ifp->n_setstate) /* call state routine if any */
      err = ifp->n_setstate(ifp, opcode);
   else
      err = 0; /* no routine == no error */

   if(!err)
   {
      /* Get here if setstate was OK - set ifOperStatus */
      if (opcode == NI_UP)
         ifp->n_mib->ifOperStatus = NI_UP;
      else
         ifp->n_mib->ifOperStatus = NI_DOWN;
   }

   UNLOCK_NET_RESOURCE(NET_RESID);

   return err;
}
Exemplo n.º 19
0
void
tcp_sleep(struct socket *so, int timeout)
{

#ifndef SUPERLOOP
   /* task must be awake to be put to sleep */
   if (tk_cur->tk_flags & TF_AWAKE)
   {
      if ((so) && (so->so_semaphore))
      {
         UNLOCK_NET_RESOURCE(NET_RESID);
         TK_SIGWAIT(NULL, so->so_semaphore, timeout);
         LOCK_NET_RESOURCE(NET_RESID);
      }
   }
   else
      dtrap();
#else
   UNLOCK_NET_RESOURCE(NET_RESID);
   TK_YIELD();
   LOCK_NET_RESOURCE(NET_RESID);
#endif

}
Exemplo n.º 20
0
static struct mbuf  * 
sockargs (void * arg, 
   int   arglen, 
   int   type)
{
   struct mbuf *  m;

   LOCK_NET_RESOURCE(NET_RESID);    /* protect mfreeq */
   m = m_getwithdata (type, arglen);
   UNLOCK_NET_RESOURCE(NET_RESID);
   if (m == NULL)
      return NULL;
   m->m_len = arglen;
   MEMCPY(mtod (m, char *), arg, arglen);
   return m;
}
Exemplo n.º 21
0
int dump_buf_estats (void * pio)
{
   u_long mlocal [MEMERR_NUM_STATS];

   LOCK_NET_RESOURCE(FREEQ_RESID);
   ENTER_CRIT_SECTION(&memestats);
   MEMCPY (&mlocal, &memestats, sizeof(memestats));
   EXIT_CRIT_SECTION(&memestats);
   UNLOCK_NET_RESOURCE(FREEQ_RESID);

   ns_printf(pio, "Regular buffer error statistics:\n");
   ns_printf(pio, "Bad buffer length %lu, Guard band violations %lu\n",mlocal[BAD_REGULAR_BUF_LEN_ERR],mlocal[GUARD_BAND_VIOLATED_ERR]);
   ns_printf(pio, "Multiple frees %lu, Inconsistent location %lu\n",mlocal[MULTIPLE_FREE_ERR],mlocal[INCONSISTENT_LOCATION_ERR]);

   return 0;
}
Exemplo n.º 22
0
/* FUNCTION: ip_raw_close()
 * 
 * Closes an endpoint.
 *
 * PARAM1: struct ipraw_ep * ep; IN - pointer to endpoint
 *                               that is to be closed
 * RETURNS: void
 */
void
ip_raw_close(struct ipraw_ep * ep)
{
   struct ipraw_ep * prev_ep;
   struct ipraw_ep * curr_ep;

   LOCK_NET_RESOURCE(NET_RESID);

   /* search the list of endpoints for the one we're supposed to close */
   for (prev_ep = NULL, curr_ep = ipraw_eps;
        curr_ep != NULL;
        curr_ep = curr_ep->ipr_next)
   {
      if (curr_ep == ep)
         break;
      prev_ep = curr_ep;
   }

   /* if we didn't find it, we can't close it, so just return */
   if (curr_ep == NULL)
   {
#ifdef NPDEBUG
      /* caller passed pointer to endpoint not in list 
       * -- not fatal, but may be programming error
       */
      dtrap();
#endif /* NPDEBUG */
      UNLOCK_NET_RESOURCE(NET_RESID);
      return;
   }

   /* unlink it from the list */
   if (prev_ep)
      prev_ep = curr_ep->ipr_next;
   else
      ipraw_eps = curr_ep->ipr_next;

   /* free its storage */
   IEP_FREE(curr_ep);

   /* and return */
   UNLOCK_NET_RESOURCE(NET_RESID);
}
Exemplo n.º 23
0
long
t_socket(int family, 
   int   type, 
   int   proto)
{
   struct socket *   so;

   INET_TRACE (INETM_SOCKET, ("SOCK:sock:family %d, typ %d, proto %d\n",
    family, type, proto));
   LOCK_NET_RESOURCE(NET_RESID);
   if ((so = socreate (family, type, proto)) == NULL) 
   {  /* can't really return error info since no socket.... */
      UNLOCK_NET_RESOURCE(NET_RESID);
      return SOCKET_ERROR;
   }
   SOC_RANGE(so);
   so->so_error = 0;
   UNLOCK_NET_RESOURCE(NET_RESID);
   return SO2LONG(so);
}
Exemplo n.º 24
0
/* FUNCTION: mbuf_list()
 * 
 * PARAM1: GIO *              GIO descriptor
 *
 * RETURNS: int               0
 */
int
mbuf_list(GIO *gio)
{
   LOCK_NET_RESOURCE(FREEQ_RESID);

   gio_printf(gio, "mbufs in use: \n");
   if (mbufq.q_head)
   {
      struct mbuf *mb;

      gio_printf(gio, "  addr    type     pkt      data   len\n");
      for (mb = (struct mbuf *)mbufq.q_head; mb; mb = mb->next)
      {
         gio_printf(gio, "%p %s %lx %lx %d\n",
                         mb, mbuftypes[mb->m_type],
                         mb->pkt, mb->m_data, mb->m_len);
      }
   }
   else
      gio_printf(gio, "  none\n");

   gio_printf(gio, "free mbufs: \n");
   if (mfreeq.q_head)
   {
      struct mbuf *mb;

      gio_printf(gio, "  addr    type     pkt      data   len\n");
      for (mb = (struct mbuf *)mfreeq.q_head; mb; mb = mb->next)
      {
         gio_printf(gio, "%p %s %lx %lx %d\n",
                         mb, mbuftypes[mb->m_type],
                         mb->pkt, mb->m_data, mb->m_len);
      }
   }
   else
      gio_printf(gio, "  none\n");

   UNLOCK_NET_RESOURCE(FREEQ_RESID);

   return (0);
}
Exemplo n.º 25
0
int
t_bind (long s, 
   struct sockaddr * addr,
   int addrlen)
{
   struct mbuf *     nam;
   struct sockaddr   sa;
   struct sockaddr * sap;
   struct socket *   so;
   int               err;

   so = LONG2SO(s);  /* convert long to socket */
   SOC_CHECK(so);
   DOMAIN_CHECK(so, addrlen);

   so->so_error = 0;
   if (addr == (struct sockaddr *)NULL) 
   {
      MEMSET ((void *)&sa, 0, sizeof(sa));
      addrlen = sizeof(sa);
      sa.sa_family = so->so_domain;
      sap = &sa;
   } else
      sap = addr;

   if ((nam = sockargs (sap, addrlen, MT_SONAME)) == NULL) 
   {
      so->so_error = ENOMEM;
      return SOCKET_ERROR;
   }
   LOCK_NET_RESOURCE(NET_RESID);
   err = sobind (so, nam);
   m_freem(nam);
   UNLOCK_NET_RESOURCE(NET_RESID);
   if (err) 
   {
      so->so_error = err;
      return SOCKET_ERROR;
   }
   return 0;
}
Exemplo n.º 26
0
/* FUNCTION: ip_raw_open()
 *
 * Opens an endpoint for reception of raw IP datagrams.
 *
 * PARAM1: u_char prot; IN - the IP protocol ID for which
 *                      datagrams are to be received, or 0
 *                      to receive traffic for all IP 
 *                      protocol IDs not otherwise handled
 *                      by the stack.
 * PARAM2: ip_addr laddr; IN - the local IP address for which
 *                        datagrams are to be received, in 
 *                        network order; or 0 to receive traffic
 *                        directed to any IP address.
 * PARAM3: ip_addr faddr; IN - the remote peer IP address from 
 *                        which datagrams are to be received, in 
 *                        network order; or 0 to receive traffic
 *                        from any peer IP address.
 * PARAM4: int (*handler)(PACKET, void *); IN - pointer to an
 *                                         upcall function to be
 *                                         called on receipt of
 *                                         matching packets
 * PARAM5: void * data; IN - opaque token to be passed to the 
 *                      upcall function; may be used to identify 
 *                      the endpoint to the upcall function
 *
 * RETURNS: a pointer to the allocated endpoint structure, or
 *          NULL if no endpoint was allocated.
 */
struct ipraw_ep *
ip_raw_open(u_char prot,
            ip_addr laddr,
            ip_addr faddr,
            int (*handler)(PACKET, void *),
            void * data)
{
   struct ipraw_ep * ep;

   LOCK_NET_RESOURCE(NET_RESID);

   /* allocate a structure for the endpoint */
   ep = (struct ipraw_ep *)IEP_ALLOC(sizeof(struct ipraw_ep));
   if (ep == NULL)
   {
#ifdef NPDEBUG
      if (NDEBUG & INFOMSG)
         dprintf("IP: Couldn't allocate ep storage.\n");
#endif
      UNLOCK_NET_RESOURCE(NET_RESID);
      return ep;
   }

   /* fill it in with the caller's requested binding */
   ep->ipr_laddr = laddr;
   ep->ipr_faddr = faddr;
   ep->ipr_prot = prot;
   ep->ipr_rcv = handler;
   ep->ipr_data = data;

   /* link it into the list 
    * (at the head, because that's simple and fast) 
    */
   ep->ipr_next = ipraw_eps;
   ipraw_eps = ep;

   /* and return the pointer to the endpoint */
   UNLOCK_NET_RESOURCE(NET_RESID);
   return ep;
}
Exemplo n.º 27
0
int igmp_input (PACKET p)
{
    u_char mode;
    int rc;

    ++igmpstats.igmp_total_rcvd;

    /* validate the received packet; if validation fails,
     * drop the packet and return */
    if ((rc = igmp_validate (p)) != IGMP_OK) goto end;

    /* determine the operating mode for IGMP on the ingress link */
    mode = p->net->igmp_oper_mode;

    /* feed packet to IGMPv1 or IGMPv2 code based on the operating
     * mode of the ingress link */
    switch (mode)
    {
#ifdef IGMP_V1
    case IGMP_MODE_V1:
        return (igmpv1_input (p));
#endif
#ifdef IGMP_V2
    case IGMP_MODE_V2:
        return (igmpv2_input (p));
#endif
    default:
        ++igmpstats.igmp_bad_oper_mode;
        rc = IGMP_ERR;
        break;
    }

end:
    /* return packet buffer back to free pool */
    LOCK_NET_RESOURCE(FREEQ_RESID);
    pk_free(p);
    UNLOCK_NET_RESOURCE(FREEQ_RESID);

    return rc;
}
Exemplo n.º 28
0
PACKET
ip_raw_alloc(int reqlen, int hdrincl)
{
   int len;
   PACKET p;

   len = (reqlen + 1) & ~1;
   if (!hdrincl)
      len += IPHSIZ;
   LOCK_NET_RESOURCE(FREEQ_RESID);
   PK_ALLOC(p, (len + MaxLnh));
   UNLOCK_NET_RESOURCE(FREEQ_RESID);
   if (p)
   {
      if (!hdrincl)
      {
         p->nb_prot += IPHSIZ;
         p->nb_plen -= IPHSIZ;
      }
   }
   return p;
}
Exemplo n.º 29
0
int
t_recvfrom(long s, 
   char *   buf,
   int   len, 
   int   flags,
   struct sockaddr * from,
   int * fromlen)
{
   struct socket *   so;
   struct mbuf *     sender = NULL;
   int   err;
   int   sendlen = len;

   so = LONG2SO(s);
   SOC_CHECK(so);
   so->so_error = 0;

   LOCK_NET_RESOURCE(NET_RESID);

   err = soreceive(so, &sender, buf, &len, flags);

   /* copy sender info from mbuf to sockaddr */
   if (sender)
   {
      MEMCPY(from, (mtod(sender, struct sockaddr *)), *fromlen );
      m_freem (sender);
   }

   UNLOCK_NET_RESOURCE(NET_RESID);

   if(err)
   {
      so->so_error = err;
      return SOCKET_ERROR;
   }

   /* OK return: amount of data actually sent */
   return (sendlen - len);
}
Exemplo n.º 30
0
int
t_shutdown(long s, int   how)
{
   struct socket *so;
   int   err;

   so = LONG2SO(s);
   SOC_CHECK(so);
   so->so_error = 0;
   INET_TRACE (INETM_SOCKET, ("INET:shutdown so %x how %d\n", so, how));

   LOCK_NET_RESOURCE(NET_RESID);
   err = soshutdown(so, how);
   UNLOCK_NET_RESOURCE(NET_RESID);

   if (err != 0)
   {
      so->so_error = err;
      return SOCKET_ERROR;
   }
   return 0;
}