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

📄 ppp.c

📁 PPP协议C语言源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
#endif
                    }
                    break;
#if defined(LQRP) && QUALITY
                case LCPopt_LQPT:
                    if (cp2[2] != 0xc0 || cp2[3] != 0x25)
                        goto rej3;
                    cp2 += 2;
                    if ((!cp2[0] || !cp2[1] || !cp2[2] || !cp2[3]) &&
                            netp->peerLQRPms == 0)
                        goto rej3;
                    netp->ownLQRPms = cp2[0] << 24 +
                                      cp2[1] << 16 +
                                      cp2[2] << 8 +
                                      cp2[3];
                    netp->ownLQRPms *= 10;
#endif
                case LCPopt_MNUM:
                    break;
                case LCPopt_RES6:
                    goto rej3;
#if COMPRESSION & 1
                case LCPopt_PCMP:
                case LCPopt_ACMP:
                    netp->hw.remopts |= 1<<us1;
                    break;
#endif
#if MP
#if 0
                case LCPopt_SNHF:   /* Not supported */
                    netp->hw.opt5 |= MPsnhf;
                    break;
#endif
                case LCPopt_ENDD:
                    if (us2 > 20 + 3)
                        goto rej3;
                    if (mpFindBundle(netno, cp2[2], us2-3, (char *)cp2+3) < 0)
                        goto rej3;
                    break;
#endif
                default:
rej3:
                   /* Build reject at +400 in buffer */
                    Nmemcpy((char *)mess+400+rejlen, cp2, us2);
                    rejlen += us2;
rej4:
                    break;
                }
            }

            if (naklen || rejlen) {
                netp->hw.remopts = 0;
                if (naklen) {
                    *cp = LCPconf_nak;      /* Nak with hint */
                    Nmemcpy((char *)cp + 4, (char *)mess + 200, naklen);
                    i2 = naklen + 4;
                }
                else if (rejlen) {
                    *cp = LCPconf_rej;      /* Reject others */
                    Nmemcpy((char *)cp + 4, (char *)mess + 400, rejlen);
                    i2 = rejlen + 4;
                }
                mess->mlen = MESSH_SZ + LHDRSZ + i2;
                cp[2] = i2 >> 8, cp[3] = i2;
                netp->state &= ~(LCPrxREQ + LCPtxACK);
            }
            else
                netp->state |= (LCPrxREQ | LCPtxACK);
            pppWrite(mess);
            break;
        case LCPconf_ack:
            if (cp[1] != netp->hw.opt1 || (prevstate & LCPtxREQ) == 0)
                goto rej1;
            if ((prevstate & LCPopen) == LCPopen)
                pppStart(netno, 1);             /* tld, restart LCP */
            else if (prevstate & LCPrxACK)      /* If ack-rcvd already, */
                netp->state = 0;                /*  send conf-req */
            else {
                netp->state |= LCPrxACK;        /* ack-rcvd */
                netp->hw.opt7 = MAXCONF;        /* Initialize restart counter */
                netp->hw.timems = TimeMS();     /* Initialize timer */
            }
            break;
        case LCPconf_nak:
        case LCPconf_rej:
            if (cp[1] != netp->hw.opt1)
                goto rej1;

           /* Find and disable unaccepted options */
            for (; i1>0; cp2+=us2) {
                us1 = cp2[0];                   /* type */
                us2 = cp2[1];                   /* length */
                i1 -= us2;                      /* length - 1 */
                if (us1 > 19 || us2 < 2)
                    break;
#if REQAUTH
                if (us1 == 3) {
#if NTRACE >= 3
                    Nprintf("PPP: Peer refused requested authentication.\n");
#endif
                    goto term;
                }
#endif
#if MP
                if (us1 > 15)
                    netp->hw.opt5 &= ~(1<<(us1-16));/* disable MP opts */
                else
#endif
                if (*cp == LCPconf_nak && us1 == LCPopt_ASYC)
                    netp->hw.ul1 = cp2[2] << 24 +
                                   cp2[3] << 16 +
                                   cp2[4] << 8 +
                                   cp2[5];
                else {
                    netp->hw.locopts &= ~(1<<us1);  /* disable option */
                    if (us1 == LCPopt_ASYC)
                        netp->hw.ul1 = 0xffffffff;
                }
            }
            if ((prevstate & LCPopen) == LCPopen)
                pppStart(netno, 1);             /* tld, restart LCP */
            else if (prevstate & LCPrxACK)
                netp->state = 0;
            else {
                netp->hw.opt7 = MAXCONF;        /* Initialize restart counter */
                netp->hw.timems = TimeMS();     /* Initialize timer */
                netp->state &= ~(LCPtxREQ | LCPrxACK);
            }
            break;
        case LCPterm_req:
            if ((prevstate & LCPopen) == LCPopen) {
                netp->state = PPPclsng;
                netp->hw.opt7 = 0;                  /* Zero restart counter */
                pppDQ(netno);
            }
            else if (prevstate != PPPclsd && prevstate != PPPclsng)
                netp->state = LCPtxREQ;             /* Wait for TO+/- */
            *cp = LCPterm_ack;                      /* Set new type */
            pppWrite(mess);                         /* Send term-ack */
            break;
        case LCPterm_ack:
            if (cp[1] != netp->hw.opt1)             /* reject bad ID */
                goto rej1;
            if (prevstate != PPPclsng)
                if ((prevstate & LCPopen) == LCPopen)
                    netp->state = 0;                /* resend conf-req */
                else
                    netp->state &= ~(LCPrxACK);
            else {                                  /* If closing/stopping, */
#if MP
                mpShut(netno);
#endif
                netp->state = PPPclsd;              /* link layer closed */
                netp->hw.opt7 = 0;
                pppDQ(netno);
                PPPSIG_LCP_DOWN(netno);
#if DIALD
                if ((netconf[netp->confix].flags & DIAL) == 0)
#endif
                {
                    PPPSIG_PPP_DOWN(netno);
                }
                pppForceDown(netno);
                return -2;
            }
        case LCPcode_rej:
#if NTRACE
            Nprintf("PPP: Peer may be using an unknown version of PPP\n");
#endif
            break;
        case LCPprot_rej:
            us1 = cp2[0] << 8 + cp2[1];
            if (us1 == PROTlqp)
                netp->hw.locopts &= ~(1<<LCPopt_LQPT);
            else if (us1 == PROTipcp) {
#if NTRACE
                Nprintf("PPP: Peer does not support IPCP!\n");
#endif
                goto term;
            }
            break;
        case LCPecho_req:
            if ((prevstate & LCPopen) == LCPopen) {
                *cp = LCPecho_rep;
#if MAGICNUM
                if (netp->hw.locopts & (1<<LCPopt_MNUM)) {
                    netp->hw.mnum = TimeMS();
                    Nmemcpy((char *)cp+4, (char *)&netp->hw.mnum, 4);
                }
                else
#endif
                    memset((char *)cp+4, 0, 4);
                pppWrite(mess);
            }
            break;
#if ECHO_TOUTMS
        case LCPecho_rep:
           /*
            ** There is no check for packet id.  This could be bad if the
            ** peer is delayed in it's responses beyond the timeout period
            ** for echo-req.  This is, however, very unlikely as the timeout
            ** period should generally be in seconds, not milliseconds.
            */
#if MAGICNUM
            if (netp->hw.locopts & (1<<LCPopt_MNUM)) {
               /* Magic number in reply shouldn't match request */
                if (memcmp(cp+4, (char *)&netp->hw.mnum, 4) != 0)
                    netp->hw.opt6--;
#if NTRACE >= 3
                else
                    Nprintf("PPP: Possible loop-back condition on echo-rep\n");
#endif
            }
            else
#endif
                netp->hw.opt6--;
#endif
        case LCPdisc_req:
            break;
        default:            /* Unknown code */
            i1 += 4;                                /* Length of packet */
            us1 = i1 + 4;                           /* Length of new packet */
            for (; i1 >= 0; i1--)                   /* Copy packet */
                cp2[i1] = cp[i1];
            *cp = LCPcode_rej;                      /* New code field */
            cp[2] = us1 >> 8, cp[3] = us1;          /* New length field */
            mess->mlen = MESSH_SZ + LHDRSZ + us1;
            pppWrite(mess);
            break;
        }
    }
    else if ((prevstate & LCPopen) != LCPopen)
        goto rej1;                          /* Only LCP until LCP is open */
#if AUTHENT & 1 || REQAUTH == PROTpap
    else if (protocol == NC2(PROTpap)) {
        switch (us1) {
#if REQAUTH == PROTpap
        case PAPauth_req:
            netp->hw.opt4 &= ~AUTHhwat;         /* Peer responded */
            cp3 = ussGetPasswd(netno, *cp2, cp2+1);
            cp2 += *cp2 + 1;
            if (strlen(cp3) == *cp2 && strncmp(cp3, cp2+1, *cp2) == 0) {
                *cp = PAPauth_ack;              /* Set response to ACK */
                cp[4] = strlen(AUTH_ACK_REPLY); /* Size of reply */
                strcpy((char *)cp+5,AUTH_ACK_REPLY);/* insert reply text */
                netp->hw.opt4 &= ~AUTHhpap;     /* Peer accepted */
            }
            else {
                *cp = PAPauth_nak;              /* Set response to NAK */
                cp[4] = strlen(AUTH_NAK_REPLY); /* Size of reply */
                strcpy((char *)cp+5,AUTH_NAK_REPLY);/* insert reply text */
#if NTRACE >= 3
                Nprintf("PPP: Peer failed PAP authentication\n");
#endif
            }
            rejlen = cp[4] + 5;                 /* Determine length */
            cp[2] = rejlen >> 8, cp[3] = rejlen;/* Set value in packet*/
            mess->mlen = MESSH_SZ + LHDRSZ + rejlen;
            pppWrite(mess);                     /* Drop it on line */
            if (*cp == PAPauth_nak) {
                PPPSIG_PAUTH_DOWN(netno);
                goto term;
            }
            else {
                PPPSIG_PAUTH_UP(netno);
            }
            break;
#endif
#if AUTHENT & 1
        case PAPauth_ack:
            netp->hw.opt4 &= ~(AUTHppap|AUTHpwat);  /* Host accepted */
            PPPSIG_HAUTH_UP(netno);
            break;
        case PAPauth_nak:
#if NTRACE >= 3
            Nprintf("PPP: Host failed PAP authentication.\n");
#endif
            PPPSIG_HAUTH_DOWN(netno);
            break;
#endif
        }
    }
#endif
#if AUTHENT & 6 || REQAUTH == PROTchap /* CHAP/MS-CHAP auth allowed */
    else if (protocol == NC2(PROTchap)) {
        switch (us1) {
#if AUTHENT & 6
        case CHAPchallenge:
            netp->hw.opt4 |= AUTHpwat;          /* Wait for success/fail */
            *cp = CHAPresponse;                 /* Signal a response (2) */
            us2 = *cp2;                         /* Value size */
#if AUTHENT & 4
            if (netp->hw.opt4 & AUTHpmsc) {
                cp3 = cp2 + 50;                 /* End of data field */
                Nmemcpy(cp3, cp2+1, us2);        /* Save challenge value */

                *cp2 = 49;                      /* value size is 49 */
                memset(cp2+1, 0, 49);           /* Zero value field */
                i2 = ((i1 = strlen(netp->hw.passwd)) > 14) ? 14 : i1;
                for (i3=0; i3 < i2*2; i3++) {
                    *((char *)cp3+8+i3*2) = netp->hw.passwd[i3];
                    *((char *)cp3+9+i3*2) = 0;
                }
                NtChallengeResponse(cp3, cp3+8, i2*2, cp2+25);
                LmChallengeResponse(cp3, (unsigned char *)netp->hw.passwd,
                        cp2+1);
                cp2[49] = USE_NT;               /* Use (0=LM, 1=NT) ChRe */
                i2 = 50;                                /* place to add id */
                rejlen = 54;                            /* add name length */
            }
#endif
#if AUTHENT & 2
            if (netp->hw.opt4 & AUTHpchp) {
               /* CHAP response:
                ** MD5(id + secret + challenge) ==> new value field
                */
                cp3 = cp2 + i1;
                *cp3 = cp[1];
                strcpy((char *)cp3+1, netp->hw.passwd); /* PassWd */
                i1 = strlen(netp->hw.passwd) + 1;       /* PassWd len + ID */
                Nmemcpy((char *)cp3+i1, cp2+1, us2);    /* Copy challenge */
                i1 += us2;                              /* Length to hash */
                *cp2 = 16;                              /* Value size is 16 */
                MD5digest(cp3, i1, cp2+1);
                i2 = 17;                                /* Place to add id */
                rejlen = 21;                            /* Add name length */
            }
#endif
            strcpy((char *)cp2 + i2, netp->hw.userid);  /* Add name */
            rejlen += strlen(netp->hw.userid);      /* Add length of name */
            cp[2] = rejlen >> 8, cp[3] = rejlen;    /* Length */
            mess->mlen = MESSH_SZ + LHDRSZ + rejlen;/* Set mess buf len */
            pppWrite(mess);
            break;
#endif
#if REQAUTH == PROTchap
        case CHAPresponse:
            if (cp[1] != netp->hw.opt1)         /* Match challenge ID */
                goto rej1;

            netp->hw.opt4 &= ~AUTHhwat;         /* Peer responded */

           /* CHAP length = 16, MS-CHAP length = 49 */
            us2 = *cp2;                         /* length of value */
            rejlen = 4;

           /* Re-create the peer's response to our challenge.
            ** Variables used:
            **   i1 is the length of the response
            **   us2 is the value size
            **   cp2 points to the value size (data area of PPP packet)
            **   cp3 will point to the challenge (in scratch area)
            **   cp4 will point to the password (derived from the userid)
            **   i2 will be the length of the new challenge value
            **
            ** CHAP:
            **   value size = 16
            **   MD5(id + secret + challenge, length, value)
            ** MS-CHAP:
            **   value size = 49
            **   NT(challenge, unicode secret, value)
            **   LM(challenge, secret, value + 24)
            **   USE_NT at value + 48 
            */
            cp3 = cp2 + i1;                     /* Point to scratch area */
            i2 = 0;                             /* Length of value to hash */
            cp4 = (unsigned char *)ussGetPasswd(netno, i1-us2-1,
                (char *)cp2+us2+1);

#if AUTH_ALG == CHAPalg_MD5
           /* Identifier*/
            cp3[i2++] = cp[1];

           /* Secret */
            strcpy((char *)cp3+i2, (char *)cp4);
            i2 += strlen((char *)cp4);
#endif

           /* Challenge */
            cp3[i2++] = (unsigned char)strlen(netp->hw.userid);
            Nmemcpy((char *)cp3+i2, (char *)&netp->hw.ul2, 4);
            i2 += 4;
            cp3[i2++] = (unsigned char)(netp->hw.ul2 >> 3);
            cp3[i2++] = (unsigned char)(netp->hw.ul2 >> 10);
            cp3[i2++] = (unsigned char)(netp->hw.ul2 >> 15);

#if AUTH_ALG == CHAPalg_MD5
            MD5digest(cp3, i2, cp3+i2);         /* HASH the challenge */
            if (memcmp(cp2+1, cp3+i2, 16) == 0)
#elif AUTH_ALG == CHAPalg_MD4
            if (cp2[49] == 1) {
               /* Make Unicode password for NT response after challenge. */
                for (i3=i2, us1=strlen((char *)cp4), us2=0; us2 < us1; us2++) {
                    cp3[i3++] = cp4[us2];
                    cp3[i3++] = 0;
                }

               /* Make NT Response (last parameter) after unicode password. */
                NtChallengeResponse(cp3, cp3+i2, us1<<1, cp3+i3);
                i2 = 25;
            }
            else if (cp2[49]

⌨️ 快捷键说明

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