1 /* 2 * PPP PAP Module 3 * 4 * Written by Toshiharu OHNO (tony-o@iij.ad.jp) 5 * 6 * Copyright (C) 1993-94, Internet Initiative Japan, Inc. 7 * All rights reserverd. 8 * 9 * Redistribution and use in source and binary forms are permitted 10 * provided that the above copyright notice and this paragraph are 11 * duplicated in all such forms and that any documentation, 12 * advertising materials, and other materials related to such 13 * distribution and use acknowledge that the software was developed 14 * by the Internet Initiative Japan, Inc. The name of the 15 * IIJ may not be used to endorse or promote products derived 16 * from this software without specific prior written permission. 17 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 18 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 19 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. 20 * 21 * $Id$ 22 * 23 * TODO: 24 */ 25 #include "fsm.h" 26 #include "lcp.h" 27 #include "pap.h" 28 #include "vars.h" 29 #include "hdlc.h" 30 #include "lcpproto.h" 31 #include "phase.h" 32 #include "auth.h" 33 34 #ifdef PASSWDAUTH 35 # include "passwdauth.h" 36 #endif 37 38 static char *papcodes[] = { 39 "???", "REQUEST", "ACK", "NAK" 40 }; 41 42 struct authinfo AuthPapInfo = { 43 SendPapChallenge, 44 }; 45 46 void 47 SendPapChallenge(papid) 48 int papid; 49 { 50 struct fsmheader lh; 51 struct mbuf *bp; 52 u_char *cp; 53 int namelen, keylen, plen; 54 55 namelen = strlen(VarAuthName); 56 keylen = strlen(VarAuthKey); 57 plen = namelen + keylen + 2; 58 #ifdef DEBUG 59 logprintf("namelen = %d, keylen = %d\n", namelen, keylen); 60 #endif 61 LogPrintf(LOG_PHASE_BIT, "PAP: %s (%s)\n", VarAuthName, VarAuthKey); 62 lh.code = PAP_REQUEST; 63 lh.id = papid; 64 lh.length = htons(plen + sizeof(struct fsmheader)); 65 bp = mballoc(plen + sizeof(struct fsmheader), MB_FSM); 66 bcopy(&lh, MBUF_CTOP(bp), sizeof(struct fsmheader)); 67 cp = MBUF_CTOP(bp) + sizeof(struct fsmheader); 68 *cp++ = namelen; 69 bcopy(VarAuthName, cp, namelen); 70 cp += namelen; 71 *cp++ = keylen; 72 bcopy(VarAuthKey, cp, keylen); 73 74 HdlcOutput(PRI_LINK, PROTO_PAP, bp); 75 } 76 77 static void 78 SendPapCode(id, code, message) 79 int id; 80 char *message; 81 int code; 82 { 83 struct fsmheader lh; 84 struct mbuf *bp; 85 u_char *cp; 86 int plen, mlen; 87 88 lh.code = code; 89 lh.id = id; 90 mlen = strlen(message); 91 plen = mlen + 1; 92 lh.length = htons(plen + sizeof(struct fsmheader)); 93 bp = mballoc(plen + sizeof(struct fsmheader), MB_FSM); 94 bcopy(&lh, MBUF_CTOP(bp), sizeof(struct fsmheader)); 95 cp = MBUF_CTOP(bp) + sizeof(struct fsmheader); 96 *cp++ = mlen; 97 bcopy(message, cp, mlen); 98 LogPrintf(LOG_PHASE_BIT, "PapOutput: %s\n", papcodes[code]); 99 HdlcOutput(PRI_LINK, PROTO_PAP, bp); 100 } 101 102 /* 103 * Validate given username and passwrd against with secret table 104 */ 105 static int 106 PapValidate(name, key) 107 u_char *name, *key; 108 { 109 int nlen, klen; 110 111 nlen = *name++; 112 klen = *key; 113 *key++ = 0; 114 key[klen] = 0; 115 #ifdef DEBUG 116 logprintf("name: %s (%d), key: %s (%d)\n", name, nlen, key, klen); 117 #endif 118 119 #ifdef PASSWDAUTH 120 if( Enabled( ConfPasswdAuth ) ) 121 { 122 LogPrintf( LOG_LCP, "PasswdAuth enabled - calling\n" ); 123 return PasswdAuth( name, key ); 124 } 125 #endif /* PASSWDAUTH */ 126 127 return(AuthValidate(SECRETFILE, name, key)); 128 } 129 130 void 131 PapInput(bp) 132 struct mbuf *bp; 133 { 134 int len = plength(bp); 135 struct fsmheader *php; 136 struct lcpstate *lcp = &LcpInfo; 137 u_char *cp; 138 139 if (len >= sizeof(struct fsmheader)) { 140 php = (struct fsmheader *)MBUF_CTOP(bp); 141 if (len >= ntohs(php->length)) { 142 if (php->code < PAP_REQUEST || php->code > PAP_NAK) 143 php->code = 0; 144 LogPrintf(LOG_PHASE_BIT, "PapInput: %s\n", papcodes[php->code]); 145 146 switch (php->code) { 147 case PAP_REQUEST: 148 cp = (u_char *) (php + 1); 149 if (PapValidate(cp, cp + *cp + 1)) { 150 SendPapCode(php->id, PAP_ACK, "Greetings!!"); 151 lcp->auth_ineed = 0; 152 if (lcp->auth_iwait == 0) 153 NewPhase(PHASE_NETWORK); 154 } else { 155 SendPapCode(php->id, PAP_NAK, "Login incorrect"); 156 LcpClose(); 157 } 158 break; 159 case PAP_ACK: 160 StopAuthTimer(&AuthPapInfo); 161 cp = (u_char *)(php + 1); 162 len = *cp++; 163 cp[len] = 0; 164 LogPrintf(LOG_PHASE_BIT, "Received PAP_ACK (%s)\n", cp); 165 if (lcp->auth_iwait == PROTO_PAP) { 166 lcp->auth_iwait = 0; 167 if (lcp->auth_ineed == 0) 168 NewPhase(PHASE_NETWORK); 169 } 170 break; 171 case PAP_NAK: 172 StopAuthTimer(&AuthPapInfo); 173 cp = (u_char *)(php + 1); 174 len = *cp++; 175 cp[len] = 0; 176 LogPrintf(LOG_PHASE_BIT, "Received PAP_NAK (%s)\n", cp); 177 LcpClose(); 178 break; 179 } 180 } 181 } 182 pfree(bp); 183 } 184