⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ipcp.c

📁 在ARM7和UC/OSII的平台上实现了GPS自动报站的功能,涉及GPS模块LEA_4S的驱动,位置速寻算法,语音芯片ISD4004的录放音驱动,LED页面管理等等.从启动代码到操作系统的移植以及到业
💻 C
📖 第 1 页 / 共 3 页
字号:
         {
            /* got here because he's trying to set our address */
            
            tryfor.ouraddr = ciaddr1;
            //ConPrintf("local IP address %u.%u.%u.%u\n",
               //PUSH_IPADDR(ciaddr1));
            #if IPCP_DEBUG
             Printu("local IP address %u.%u.%u.%u\n",
               PUSH_IPADDR(ciaddr1)); 
            #endif
          }
	 else {
            #if IPCP_DEBUG
	   Printu("no acceptr_local\r\n");
	   #endif
         }
         if (go->accept_remote && ciaddr2)   /* Does he know his? */
         {
            tryfor.hisaddr = ciaddr2;
           // ConPrintf("remote IP address %u.%u.%u.%u\n",
              // PUSH_IPADDR(ciaddr2) );
         }
	 /*if (mppp->states[IPCP_STATE] != ST_OPENED)
           MEMCPY(go, &tryfor, sizeof(tryfor) );
	 */
         break;
      case CI_COMPRESSTYPE:
         /* Accept the peer's value of maxslotindex provided that it
          * is less than what we asked for.  Turn off slot-ID compression
          * if the peer wants.  Send old-style compress-type option if
          * the peer wants.
          */
         if(go->neg_vj == 0)
            tryfor.neg_vj = 1;
         cishort = ppp_getshort(p + 2);
         if(cilen == CILEN_VJ)
         {
            if (cishort == IPCP_VJ_COMP)
            {
               cimaxslotindex = *(p + 4);
               cicflag = *(p + 5);
               tryfor.old_vj = 0;
               if (cimaxslotindex < go->maxslotindex)
                  tryfor.maxslotindex = cimaxslotindex;
               if (!cicflag)
                  tryfor.cflag = 0;
            }
            else
            {
               tryfor.neg_vj = 0;
            }
         }
         else if(cilen == CILEN_COMPRESS)
         {
            if((cishort == IPCP_VJ_COMP) || (cishort == IPCP_VJ_COMP_OLD))
            {
               tryfor.old_vj = 1;
               tryfor.vj_protocol = cishort;
            }
            else
            {
               tryfor.neg_vj = 0;
            }
         }
         else
         {
          //  ConPrintf("ipcp rcv NAK: bad VJ length %d\n", cilen);
            return 1;
         }
         break;
#ifdef PPP_DNS
      case CI_DNSADDR_PRI:
         if(go->neg_dnsaddr_pri == 0)
            tryfor.neg_dnsaddr_pri = 1;
         goto set_dns_addr;
      case CI_DNSADDR_SEC:
         if(go->neg_dnsaddr_sec == 0)
            tryfor.neg_dnsaddr_sec = 1;
set_dns_addr:
         /* most of the rest of this case code is common to the primary
          * DNS server address option and the secondary DNS server address
          * option.
          */
         longval = ppp_getlong(p + 2); /* extract DNS server address */
         ciaddr1 = htonl(longval);     /* make net endian for storage */

         /* Accept the nameserver addresses only if the
          * accept_dnsaddrs flag is set.
          */
         if (ciaddr1 && go->accept_dnsaddrs) /* Will we allow this? */
         {
            /* got here because he's trying to set our address */
            if(*p == CI_DNSADDR_PRI)   /* primary or secondary? */
               tryfor.dnsaddr_pri = ciaddr1;
            else
               tryfor.dnsaddr_sec = ciaddr1;
            //ConPrintf("ipcp NAK: DNS (0x%x) address %u.%u.%u.%u \n",
               //(unsigned)(*p), PUSH_IPADDR(ciaddr1) );
         }
         break;
#else
      case CI_DNSADDR_PRI:
      case CI_DNSADDR_SEC:
      break;
#endif   /* PPP_DNS */
      default:
        // ConPrintf("ipcp rcv NAK: unknown option 0x%x\n", *p);
         return 1;
      }
      p += cilen;    /* bump pointer to NAK options */
      len -= cilen;
   }

   /*if(len != 0)
   {
      //ConPrintf("ipcp odd NAK len\n");
      return 1;
   } */

   /* Nak pkt seems OK. Update "go" from tmp "tryfor" */
   if (mppp->states[IPCP_STATE] != ST_OPENED)
      MEMCPY(go, &tryfor, sizeof(tryfor) );

   return 0;
}


/* FUNCTION: ipcp_rejci()
 *
 * ipcp_rejci - Peer rejected some of our CIs.
 *
 * 
 * PARAM1: M_PPP mppp
 * PARAM2: u_char *p
 * PARAM3: int len
 *
 * RETURNS: One of the CI reject events:
 *     EV_RXJC - unrecoverable rejection, kill session.
 *     EV_RXJP - tolerable rejection, try other option.
 *     EV_NOEVENT - packet was badly formed, ignore it.
 */

int
ipcp_rejci(M_PPP mppp, u_char * p, int len)
{
   u_char   cimaxslotindex;
   u_char   ciflag;
   u_char   cilen;
   u_short  cishort;
   u_long   cilong;
   ipcp_options tryfor;   /* options to request next time */
   ipcp_options * go;

#ifdef   PPP_OLDFORMS
   u_long   l;
#endif

   go = &mppp->ipcp_gotoptions;

   /* Initialize "tryfor" options from last set received */
   MEMCPY(&tryfor, go, sizeof(*go));

   while (len > 0)
   {
      cilen = *(p + 1);
      switch(*p)
      {
      case CI_ADDRS:
      case CI_ADDR:
         if (go->neg_addr == 0)
            break;
         cilong = ppp_getlong(p + 2);
         cilong = htonl(cilong);

         /* Check rejected value. */
         if (cilong != (u_long)go->ouraddr)
            goto bad_rej;
#ifdef PPP_OLDFORMS
         if (go->old_addrs && (*p == CI_ADDRS))
         {
            /* Extract and check rejected value. */
            l = ppp_getlong(p);
            cilong = htonl(l);
            if (cilong != go->hisaddr)
               goto bad_rej;
         }
#endif   /* PPP_OLDFORMS */
         /* He rejected our IP assignment. Don't negotiate this anymore */
         tryfor.neg_addr = 0;
         break;
      case CI_COMPRESSTYPE:
         if(go->neg_vj == 0)
            goto bad_rej;
         cishort = ppp_getshort(p + 2);
         /* Check rejected value. */
         if (cishort != go->vj_protocol)  /* we only support VJ header compression */
            goto bad_rej;
         if (go->old_vj == 0)
         {
            cimaxslotindex = *(p + 4);
            if (cimaxslotindex != go->maxslotindex)
               goto bad_rej;
            ciflag = *(p + 5);
            if (ciflag != go->cflag)
               goto bad_rej;
         }
         tryfor.neg_vj = 0;      /* don't ask for this anymore */
         break;
#ifdef PPP_DNS
      case CI_DNSADDR_PRI:
         if (go->neg_dnsaddr_pri == 0)
            goto bad_rej;
         cilong = ppp_getlong(p + 2);
         if (cilong != (u_long)go->dnsaddr_pri)
            goto bad_rej;
         tryfor.neg_dnsaddr_pri = 0;
         break;
      case CI_DNSADDR_SEC:
         if (go->neg_dnsaddr_sec == 0)
            return EV_NOEVENT;
         cilong = ppp_getlong(p + 2);
         if (cilong != (u_long)go->dnsaddr_sec)
            goto bad_rej;
         tryfor.neg_dnsaddr_sec = 0;
         break;
#endif   /* PPP_DNS */
      default:
         goto bad_rej;
      }
      p += cilen;
      len -= cilen;
   }

   if(len != 0)
   {
      //ConPrintf("ipcp_rejci: bad Rej pkt len\n");
      return EV_NOEVENT;
   }

   /* Make "tryfor" list the current "got" list */
   if (mppp->states[IPCP_STATE] != ST_OPENED)
      MEMCPY(go, &tryfor, sizeof(tryfor));

   return EV_RXJP;

bad_rej:
  // ConPrintf("ipcp_rejci: bad Rej pkt at opt 0x%x\n", *p);
   return EV_NOEVENT;
}



/* FUNCTION: ipcp_reqci()
 *
 * ipcp_reqci - Check the peer's requested CIs and build appropriate 
 * response in input packet. If reject_if_disagree is non-zero, doesn't 
 * return CONFNAK; returns CONFREJ if it can't return CONFACK.
 *
 * PARAM1: M_PPP mppp
 * PARAM2: u_char * inp - recevied REQ data
 * PARAM3: int *    len - (IN/OUT) length of buffer
 * PARAM4: int reject_if_disagree
 *
 * RETURNS: CONFACK, CONFNAK or CONFREJ
 */

int
ipcp_reqci(M_PPP mppp, 
   u_char * inp,           /* received option list (CIs) */
   int * lenp,             /* Length of inp */
   int   reject_if_disagree)
{
   u_short  cilen, citype; /* Parsed len, type */
   u_long   tl;            /* Parsed address  values */
   u_long   ciaddr1;
   int      rc =  CONFACK; /* Final packet return code */
   int      orc;           /* Individual option return code */
   u_char * p;             /* Pointer to next char to parse */
   u_char * ucp;           /* Pointer to current output char */
   int      len  = *lenp;  /* Length left */
   u_char   nakaddrdone = 0; /* flag: have nak'ed (his) address */
   ipcp_options * wo = &mppp->ipcp_wantoptions;
   ipcp_options * ho = &mppp->ipcp_hisoptions;

#ifdef PPP_OLDFORMS
   ipcp_options * go = &mppp->ipcp_gotoptions;
#endif   /* PPP_OLDFORMS */

#ifdef PPP_VJC
   u_char   maxslotindex;
   u_char   cflag;
   u_short  cishort;       /* Parsed short value */
#endif   /* PPP_VJC */

   #if IPCP_DEBUG
   Printu("ipcp_reqci\r\n");
   #endif
   /* Reset all his options. */
   MEMSET(ho, 0, sizeof(*ho));

   p = ucp = inp;

   /* loop through received options list. */
   while (len) 
   {
      orc = CONFACK;          /* Assume success */
      citype = *p;            /* Parse CI type */
      cilen = *(p+1);         /* Parse CI length */
      if ((len < 2) ||        /* Not enough data for CI header or */
          (cilen < 2) ||      /*  CI length too small or */
          (cilen > (u_short)len))   /*  CI length too big? */
      {
        // ConPrintf("ipcp_reqci: bad CI length on opt 0x%x", citype);
         orc = CONFREJ;       /* Reject bad CI */
         cilen = (u_char)len; /* Reject till end of packet */
         len = 0;             /* Don't loop again */
         goto endswitch;
      }
      len -= cilen;        /* Adjust remaining length */

      switch (citype)         /* Check CI type */
      {
      case CI_ADDR:
      case CI_ADDRS:
         //ConPrintf("ipcp: received ADDR ");
         tl = ppp_getlong(p + 2);      /* Parse source address (his) */
         ciaddr1 = htonl(tl);
         //ConPrintf("IP:%u.%u.%u.%u:", PUSH_IPADDR(ciaddr1));
         /* If he has no address and we have no address to give him,
          * reject this CI -- we can't help.
          */
         if((ciaddr1 == 0) &&
            (wo->hisaddr == 0))
         {
            wo->req_addr = 0;   /* and don't ask for his address later */
            orc = CONFREJ;
            break;
         }

         /*
          * If we have an address for the peer, and either he disagrees
          * with us and we don't want to accept his address, or he 
          * doesn't have an address, then NAK it with our idea.
          * In particular, if we don't know his address, but he does,
          * then accept it.
          */
         if((wo->hisaddr != 0) &&
            (((ciaddr1 != wo->hisaddr) && (!wo->accept_remote)) ||
             (ciaddr1 == 0)))
         {
            orc = CONFNAK;
            if (!reject_if_disagree) 
            {
               tl = ntohl(wo->hisaddr);
               ppp_putlong(p + 2, tl);
            }
            nakaddrdone = 1;
            break;
         }

#ifdef PPP_OLDFORMS
         if(citype == CI_ADDRS)
         {
            u_long   ciaddr2;

            /* If he doesn't know our address, or if we both have our address
             * but disagree about it, then NAK it with our idea.
             */
            tl = ppp_getlong(p + 6);          /* Parse desination address (ours) */
            ciaddr2 = htonl(tl);
            //ConPrintf("%u.%u.%u.%u", PUSH_IPADDR(ciaddr2) );
            if (ciaddr2 != wo->ouraddr) 
            {
               if (ciaddr2 == 0 || !wo->accept_local) 
               {
                  orc = CONFNAK;
                  if (!reject_if_disagree) 
                  {
                     tl = ntohl(wo->ouraddr);
                     ppp_putlong(p + 6, tl);
                  }
               } 

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -