121 |
PDDATA /* Process data byte. */ |
PDDATA /* Process data byte. */ |
122 |
} PPPDevStates; |
} PPPDevStates; |
123 |
|
|
124 |
|
#define ESCAPE_P(accm, c) ((accm)[(c) >> 3] & pppACCMMask[c & 0x07]) |
125 |
|
|
126 |
/************************/ |
/************************/ |
127 |
/*** LOCAL DATA TYPES ***/ |
/*** LOCAL DATA TYPES ***/ |
142 |
char inEscaped; /* Escape next character. */ |
char inEscaped; /* Escape next character. */ |
143 |
u16_t inProtocol; /* The input protocol code. */ |
u16_t inProtocol; /* The input protocol code. */ |
144 |
u16_t inFCS; /* Input Frame Check Sequence value. */ |
u16_t inFCS; /* Input Frame Check Sequence value. */ |
|
u16_t inLen; /* Input packet length. */ |
|
145 |
int mtu; /* Peer's mru */ |
int mtu; /* Peer's mru */ |
146 |
int pcomp; /* Does peer accept protocol compression? */ |
int pcomp; /* Does peer accept protocol compression? */ |
147 |
int accomp; /* Does peer accept addr/ctl compression? */ |
int accomp; /* Does peer accept addr/ctl compression? */ |
155 |
|
|
156 |
struct netif *netif; |
struct netif *netif; |
157 |
|
|
158 |
struct ip_addr our_ipaddr, his_ipaddr, netmask, dns1, dns2; |
struct ppp_addrs addrs; |
159 |
|
|
160 |
void (*linkStatusCB)(void *arg, int errCode); |
void (*linkStatusCB)(void *ctx, int errCode, void *arg); |
161 |
void *linkStatusArg; |
void *linkStatusCtx; |
162 |
|
|
163 |
} PPPControl; |
} PPPControl; |
164 |
|
|
180 |
static void pppMain(void *pd); |
static void pppMain(void *pd); |
181 |
static void pppDrop(PPPControl *pc); |
static void pppDrop(PPPControl *pc); |
182 |
static void pppInProc(int pd, u_char *s, int l); |
static void pppInProc(int pd, u_char *s, int l); |
|
static struct pbuf *pppMPutC(u_char c, ext_accm *outACCM, struct pbuf *nb); |
|
|
static struct pbuf *pppMPutRaw(u_char c, struct pbuf *nb); |
|
|
|
|
|
#define ESCAPE_P(accm, c) ((accm)[(c) >> 3] & pppACCMMask[c & 0x07]) |
|
183 |
|
|
184 |
|
|
185 |
/******************************/ |
/******************************/ |
335 |
* established before calling this. |
* established before calling this. |
336 |
* Return a new PPP connection descriptor on success or |
* Return a new PPP connection descriptor on success or |
337 |
* an error code (negative) on failure. */ |
* an error code (negative) on failure. */ |
338 |
int pppOpen(sio_fd_t fd, void (*linkStatusCB)(void *arg, int errCode), void *linkStatusArg) |
int pppOpen(sio_fd_t fd, void (*linkStatusCB)(void *ctx, int errCode, void *arg), void *linkStatusCtx) |
339 |
{ |
{ |
340 |
PPPControl *pc; |
PPPControl *pc; |
341 |
int pd; |
int pd; |
380 |
pc->outACCM[15] = 0x60; |
pc->outACCM[15] = 0x60; |
381 |
|
|
382 |
pc->linkStatusCB = linkStatusCB; |
pc->linkStatusCB = linkStatusCB; |
383 |
pc->linkStatusArg = linkStatusArg; |
pc->linkStatusCtx = linkStatusCtx; |
384 |
|
|
385 |
sys_thread_new(pppMain, (void*)pd, PPP_THREAD_PRIO); |
sys_thread_new(pppMain, (void*)pd, PPP_THREAD_PRIO); |
386 |
if(!linkStatusCB) { |
if(!linkStatusCB) { |
452 |
#endif /* LINK_STATS */ |
#endif /* LINK_STATS */ |
453 |
} |
} |
454 |
|
|
455 |
|
/* |
456 |
|
* pppAppend - append given character to end of given pbuf. If outACCM |
457 |
|
* is not NULL and the character needs to be escaped, do so. |
458 |
|
* If pbuf is full, append another. |
459 |
|
* Return the current pbuf. |
460 |
|
*/ |
461 |
|
static struct pbuf *pppAppend(u_char c, struct pbuf *nb, ext_accm *outACCM) |
462 |
|
{ |
463 |
|
struct pbuf *tb = nb; |
464 |
|
|
465 |
|
/* Make sure there is room for the character and an escape code. |
466 |
|
* Sure we don't quite fill the buffer if the character doesn't |
467 |
|
* get escaped but is one character worth complicating this? */ |
468 |
|
/* Note: We assume no packet header. */ |
469 |
|
if (nb && (PBUF_POOL_BUFSIZE - nb->len) < 2) { |
470 |
|
tb = pbuf_alloc(PBUF_RAW, 0, PBUF_POOL); |
471 |
|
if (tb) { |
472 |
|
nb->next = tb; |
473 |
|
} |
474 |
|
#ifdef LINK_STATS |
475 |
|
else { |
476 |
|
lwip_stats.link.memerr++; |
477 |
|
} |
478 |
|
#endif /* LINK_STATS */ |
479 |
|
nb = tb; |
480 |
|
} |
481 |
|
if (nb) { |
482 |
|
if (outACCM && ESCAPE_P(*outACCM, c)) { |
483 |
|
*((u_char*)nb->payload + nb->len++) = PPP_ESCAPE; |
484 |
|
*((u_char*)nb->payload + nb->len++) = c ^ PPP_TRANS; |
485 |
|
} |
486 |
|
else |
487 |
|
*((u_char*)nb->payload + nb->len++) = c; |
488 |
|
} |
489 |
|
|
490 |
|
return tb; |
491 |
|
} |
492 |
|
|
493 |
/* Send a packet on the given connection. */ |
/* Send a packet on the given connection. */ |
494 |
static err_t pppifOutput(struct netif *netif, struct pbuf *pb, struct ip_addr *ipaddr) |
static err_t pppifOutput(struct netif *netif, struct pbuf *pb, struct ip_addr *ipaddr) |
495 |
{ |
{ |
570 |
|
|
571 |
/* Build the PPP header. */ |
/* Build the PPP header. */ |
572 |
if ((sys_jiffies() - pc->lastXMit) >= PPP_MAXIDLEFLAG) |
if ((sys_jiffies() - pc->lastXMit) >= PPP_MAXIDLEFLAG) |
573 |
tailMB = pppMPutRaw(PPP_FLAG, tailMB); |
tailMB = pppAppend(PPP_FLAG, tailMB, NULL); |
574 |
pc->lastXMit = sys_jiffies(); |
pc->lastXMit = sys_jiffies(); |
575 |
if (!pc->accomp) { |
if (!pc->accomp) { |
576 |
fcsOut = PPP_FCS(fcsOut, PPP_ALLSTATIONS); |
fcsOut = PPP_FCS(fcsOut, PPP_ALLSTATIONS); |
577 |
tailMB = pppMPutC(PPP_ALLSTATIONS, &pc->outACCM, tailMB); |
tailMB = pppAppend(PPP_ALLSTATIONS, tailMB, &pc->outACCM); |
578 |
fcsOut = PPP_FCS(fcsOut, PPP_UI); |
fcsOut = PPP_FCS(fcsOut, PPP_UI); |
579 |
tailMB = pppMPutC(PPP_UI, &pc->outACCM, tailMB); |
tailMB = pppAppend(PPP_UI, tailMB, &pc->outACCM); |
580 |
} |
} |
581 |
if (!pc->pcomp || protocol > 0xFF) { |
if (!pc->pcomp || protocol > 0xFF) { |
582 |
c = (protocol >> 8) & 0xFF; |
c = (protocol >> 8) & 0xFF; |
583 |
fcsOut = PPP_FCS(fcsOut, c); |
fcsOut = PPP_FCS(fcsOut, c); |
584 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
585 |
} |
} |
586 |
c = protocol & 0xFF; |
c = protocol & 0xFF; |
587 |
fcsOut = PPP_FCS(fcsOut, c); |
fcsOut = PPP_FCS(fcsOut, c); |
588 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
589 |
|
|
590 |
/* Load packet. */ |
/* Load packet. */ |
591 |
for(p = pb; p; p = p->next) { |
for(p = pb; p; p = p->next) { |
601 |
fcsOut = PPP_FCS(fcsOut, c); |
fcsOut = PPP_FCS(fcsOut, c); |
602 |
|
|
603 |
/* Copy to output buffer escaping special characters. */ |
/* Copy to output buffer escaping special characters. */ |
604 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
605 |
} |
} |
606 |
} |
} |
607 |
|
|
608 |
/* Add FCS and trailing flag. */ |
/* Add FCS and trailing flag. */ |
609 |
c = ~fcsOut & 0xFF; |
c = ~fcsOut & 0xFF; |
610 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
611 |
c = (~fcsOut >> 8) & 0xFF; |
c = (~fcsOut >> 8) & 0xFF; |
612 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
613 |
tailMB = pppMPutRaw(PPP_FLAG, tailMB); |
tailMB = pppAppend(PPP_FLAG, tailMB, NULL); |
614 |
|
|
615 |
/* If we failed to complete the packet, throw it away. */ |
/* If we failed to complete the packet, throw it away. */ |
616 |
if (!tailMB) { |
if (!tailMB) { |
719 |
/* If the link has been idle, we'll send a fresh flag character to |
/* If the link has been idle, we'll send a fresh flag character to |
720 |
* flush any noise. */ |
* flush any noise. */ |
721 |
if ((sys_jiffies() - pc->lastXMit) >= PPP_MAXIDLEFLAG) |
if ((sys_jiffies() - pc->lastXMit) >= PPP_MAXIDLEFLAG) |
722 |
tailMB = pppMPutRaw(PPP_FLAG, tailMB); |
tailMB = pppAppend(PPP_FLAG, tailMB, NULL); |
723 |
pc->lastXMit = sys_jiffies(); |
pc->lastXMit = sys_jiffies(); |
724 |
|
|
725 |
/* Load output buffer. */ |
/* Load output buffer. */ |
730 |
fcsOut = PPP_FCS(fcsOut, c); |
fcsOut = PPP_FCS(fcsOut, c); |
731 |
|
|
732 |
/* Copy to output buffer escaping special characters. */ |
/* Copy to output buffer escaping special characters. */ |
733 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
734 |
} |
} |
735 |
|
|
736 |
/* Add FCS and trailing flag. */ |
/* Add FCS and trailing flag. */ |
737 |
c = ~fcsOut & 0xFF; |
c = ~fcsOut & 0xFF; |
738 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
739 |
c = (~fcsOut >> 8) & 0xFF; |
c = (~fcsOut >> 8) & 0xFF; |
740 |
tailMB = pppMPutC(c, &pc->outACCM, tailMB); |
tailMB = pppAppend(c, tailMB, &pc->outACCM); |
741 |
tailMB = pppMPutRaw(PPP_FLAG, tailMB); |
tailMB = pppAppend(PPP_FLAG, tailMB, NULL); |
742 |
|
|
743 |
/* If we failed to complete the packet, throw it away. |
/* If we failed to complete the packet, throw it away. |
744 |
* Otherwise send it. */ |
* Otherwise send it. */ |
745 |
if (!tailMB) { |
if (!tailMB) { |
746 |
PPPDEBUG((LOG_WARNING, |
PPPDEBUG((LOG_WARNING, |
747 |
"pppWrite[%d]: Alloc err - dropping nBuf len=%d\n", pd, headMB->len)); |
"pppWrite[%d]: Alloc err - dropping pbuf len=%d\n", pd, headMB->len)); |
748 |
/* "pppWrite[%d]: Alloc err - dropping %d:%.*H", pd, headMB->len, LWIP_MIN(headMB->len * 2, 40), headMB->payload)); */ |
/* "pppWrite[%d]: Alloc err - dropping %d:%.*H", pd, headMB->len, LWIP_MIN(headMB->len * 2, 40), headMB->payload)); */ |
749 |
pbuf_free(headMB); |
pbuf_free(headMB); |
750 |
#ifdef LINK_STATS |
#ifdef LINK_STATS |
961 |
} else { |
} else { |
962 |
if(pc->netif) |
if(pc->netif) |
963 |
netif_remove(pc->netif); |
netif_remove(pc->netif); |
964 |
pc->netif = netif_add(&pc->our_ipaddr, &pc->netmask, &pc->his_ipaddr, (void *)pd, pppifNetifInit, ip_input); |
pc->netif = netif_add(&pc->addrs.our_ipaddr, &pc->addrs.netmask, &pc->addrs.his_ipaddr, (void *)pd, pppifNetifInit, ip_input); |
965 |
if(pc->netif) { |
if(pc->netif) { |
966 |
pc->if_up = 1; |
pc->if_up = 1; |
967 |
pc->errCode = 0; |
pc->errCode = PPPERR_NONE; |
968 |
|
|
969 |
if(pc->linkStatusCB) |
PPPDEBUG((LOG_DEBUG, "sifup: unit %d: linkStatusCB=%lx errCode=%d\n", pd, pc->linkStatusCB, pc->errCode)); |
970 |
pc->linkStatusCB(pc->linkStatusArg, pc->errCode); |
if(pc->linkStatusCB) |
971 |
|
pc->linkStatusCB(pc->linkStatusCtx, pc->errCode, &pc->addrs); |
972 |
} else { |
} else { |
973 |
st = 0; |
st = 0; |
974 |
PPPDEBUG((LOG_ERR, "sifup[%d]: netif_add failed\n", pd)); |
PPPDEBUG((LOG_ERR, "sifup[%d]: netif_add failed\n", pd)); |
983 |
*/ |
*/ |
984 |
int sifnpmode(int u, int proto, enum NPmode mode) |
int sifnpmode(int u, int proto, enum NPmode mode) |
985 |
{ |
{ |
986 |
(void)u; |
(void)u; |
987 |
(void)proto; |
(void)proto; |
988 |
(void)mode; |
(void)mode; |
989 |
return 0; |
return 0; |
990 |
} |
} |
991 |
|
|
992 |
/* |
/* |
1005 |
if(pc->netif) |
if(pc->netif) |
1006 |
netif_remove(pc->netif); |
netif_remove(pc->netif); |
1007 |
pc->netif = NULL; |
pc->netif = NULL; |
1008 |
|
PPPDEBUG((LOG_DEBUG, "sifdown: unit %d: linkStatusCB=%lx errCode=%d\n", pd, pc->linkStatusCB, pc->errCode)); |
1009 |
if(pc->linkStatusCB) |
if(pc->linkStatusCB) |
1010 |
pc->linkStatusCB(pc->linkStatusArg, PPPERR_CONNECT); |
pc->linkStatusCB(pc->linkStatusCtx, PPPERR_CONNECT, NULL); |
1011 |
} |
} |
1012 |
return st; |
return st; |
1013 |
} |
} |
1031 |
st = 0; |
st = 0; |
1032 |
PPPDEBUG((LOG_WARNING, "sifup[%d]: bad parms\n", pd)); |
PPPDEBUG((LOG_WARNING, "sifup[%d]: bad parms\n", pd)); |
1033 |
} else { |
} else { |
1034 |
memcpy(&pc->our_ipaddr, &o, sizeof(o)); |
memcpy(&pc->addrs.our_ipaddr, &o, sizeof(o)); |
1035 |
memcpy(&pc->his_ipaddr, &h, sizeof(h)); |
memcpy(&pc->addrs.his_ipaddr, &h, sizeof(h)); |
1036 |
memcpy(&pc->netmask, &m, sizeof(m)); |
memcpy(&pc->addrs.netmask, &m, sizeof(m)); |
1037 |
memcpy(&pc->dns1, &ns1, sizeof(ns1)); |
memcpy(&pc->addrs.dns1, &ns1, sizeof(ns1)); |
1038 |
memcpy(&pc->dns2, &ns2, sizeof(ns2)); |
memcpy(&pc->addrs.dns2, &ns2, sizeof(ns2)); |
1039 |
} |
} |
1040 |
return st; |
return st; |
1041 |
} |
} |
1059 |
st = 0; |
st = 0; |
1060 |
PPPDEBUG((LOG_WARNING, "sifup[%d]: bad parms\n", pd)); |
PPPDEBUG((LOG_WARNING, "sifup[%d]: bad parms\n", pd)); |
1061 |
} else { |
} else { |
1062 |
IP4_ADDR(&pc->our_ipaddr, 0,0,0,0); |
IP4_ADDR(&pc->addrs.our_ipaddr, 0,0,0,0); |
1063 |
IP4_ADDR(&pc->his_ipaddr, 0,0,0,0); |
IP4_ADDR(&pc->addrs.his_ipaddr, 0,0,0,0); |
1064 |
IP4_ADDR(&pc->netmask, 255,255,255,0); |
IP4_ADDR(&pc->addrs.netmask, 255,255,255,0); |
1065 |
IP4_ADDR(&pc->dns1, 0,0,0,0); |
IP4_ADDR(&pc->addrs.dns1, 0,0,0,0); |
1066 |
IP4_ADDR(&pc->dns2, 0,0,0,0); |
IP4_ADDR(&pc->addrs.dns2, 0,0,0,0); |
1067 |
} |
} |
1068 |
return st; |
return st; |
1069 |
} |
} |
1113 |
void |
void |
1114 |
pppMainWakeup(int pd) |
pppMainWakeup(int pd) |
1115 |
{ |
{ |
1116 |
|
PPPDEBUG((LOG_DEBUG, "pppMainWakeup: unit %d\n", pd)); |
1117 |
sio_read_abort(pppControl[pd].fd); |
sio_read_abort(pppControl[pd].fd); |
1118 |
} |
} |
1119 |
|
|
1128 |
{ |
{ |
1129 |
int pd = (int)arg; |
int pd = (int)arg; |
1130 |
|
|
1131 |
|
PPPDEBUG((LOG_DEBUG, "pppStartCB: unit %d\n", pd)); |
1132 |
lcp_lowerup(pd); |
lcp_lowerup(pd); |
1133 |
lcp_open(pd); /* Start protocol */ |
lcp_open(pd); /* Start protocol */ |
1134 |
} |
} |
1138 |
{ |
{ |
1139 |
int pd = (int)arg; |
int pd = (int)arg; |
1140 |
|
|
1141 |
|
PPPDEBUG((LOG_DEBUG, "pppStopCB: unit %d\n", pd)); |
1142 |
lcp_close(pd, "User request"); |
lcp_close(pd, "User request"); |
1143 |
} |
} |
1144 |
|
|
1147 |
{ |
{ |
1148 |
int pd = (int)arg; |
int pd = (int)arg; |
1149 |
|
|
1150 |
|
PPPDEBUG((LOG_DEBUG, "pppHupCB: unit %d\n", pd)); |
1151 |
lcp_lowerdown(pd); |
lcp_lowerdown(pd); |
1152 |
link_terminated(pd); |
link_terminated(pd); |
1153 |
} |
} |
1174 |
/* |
/* |
1175 |
* Start the connection and handle incoming events (packet or timeout). |
* Start the connection and handle incoming events (packet or timeout). |
1176 |
*/ |
*/ |
1177 |
ppp_trace(LOG_NOTICE, "Connecting\n"); |
PPPDEBUG((LOG_INFO, "pppMain: unit %d: Connecting\n", pd)); |
1178 |
tcpip_callback(pppStartCB, arg); |
tcpip_callback(pppStartCB, arg); |
1179 |
while (lcp_phase[pd] != PHASE_DEAD) { |
while (lcp_phase[pd] != PHASE_DEAD) { |
1180 |
if (pc->kill_link) { |
if (pc->kill_link) { |
1181 |
|
PPPDEBUG((LOG_DEBUG, "pppMainWakeup: unit %d kill_link -> pppStopCB\n", pd)); |
1182 |
pc->errCode = PPPERR_USER; |
pc->errCode = PPPERR_USER; |
1183 |
/* This will leave us at PHASE_DEAD. */ |
/* This will leave us at PHASE_DEAD. */ |
1184 |
tcpip_callback(pppStopCB, arg); |
tcpip_callback(pppStopCB, arg); |
1185 |
pc->kill_link = 0; |
pc->kill_link = 0; |
1186 |
} |
} |
1187 |
else if (pc->sig_hup) { |
else if (pc->sig_hup) { |
1188 |
|
PPPDEBUG((LOG_DEBUG, "pppMainWakeup: unit %d sig_hup -> pppHupCB\n", pd)); |
1189 |
pc->sig_hup = 0; |
pc->sig_hup = 0; |
1190 |
tcpip_callback(pppHupCB, arg); |
tcpip_callback(pppHupCB, arg); |
1191 |
} else { |
} else { |
1192 |
int c = sio_read(pc->fd, p->payload, p->len); |
int c = sio_read(pc->fd, p->payload, p->len); |
1193 |
if(c > 0) { |
if(c > 0) { |
1194 |
pppInProc(pd, p->payload, c); |
pppInProc(pd, p->payload, c); |
1195 |
|
} else { |
1196 |
|
PPPDEBUG((LOG_DEBUG, "pppMainWakeup: unit %d sio_read len=%d returned %d\n", pd, p->len, c)); |
1197 |
|
sys_msleep(250); /* give other tasks a chance to run */ |
1198 |
} |
} |
1199 |
} |
} |
1200 |
} |
} |
1201 |
|
PPPDEBUG((LOG_INFO, "pppMain: unit %d: PHASE_DEAD\n", pd)); |
1202 |
pbuf_free(p); |
pbuf_free(p); |
1203 |
|
|
1204 |
out: |
out: |
1205 |
|
PPPDEBUG((LOG_DEBUG, "pppMain: unit %d: linkStatusCB=%lx errCode=%d\n", pd, pc->linkStatusCB, pc->errCode)); |
1206 |
if(pc->linkStatusCB) |
if(pc->linkStatusCB) |
1207 |
pc->linkStatusCB(pc->linkStatusArg, pc->errCode ? pc->errCode : PPPERR_PROTOCOL); |
pc->linkStatusCB(pc->linkStatusCtx, pc->errCode ? pc->errCode : PPPERR_PROTOCOL, NULL); |
1208 |
|
|
1209 |
pc->openFlag = 0; |
pc->openFlag = 0; |
1210 |
} |
} |
1274 |
switch(protocol) { |
switch(protocol) { |
1275 |
case PPP_VJC_COMP: /* VJ compressed TCP */ |
case PPP_VJC_COMP: /* VJ compressed TCP */ |
1276 |
#if VJ_SUPPORT > 0 |
#if VJ_SUPPORT > 0 |
1277 |
PPPDEBUG((LOG_INFO, "pppInput[%d]: vj_comp in nBuf len=%d\n", pd, nb->len)); |
PPPDEBUG((LOG_INFO, "pppInput[%d]: vj_comp in pbuf len=%d\n", pd, nb->len)); |
1278 |
/* |
/* |
1279 |
* Clip off the VJ header and prepend the rebuilt TCP/IP header and |
* Clip off the VJ header and prepend the rebuilt TCP/IP header and |
1280 |
* pass the result to IP. |
* pass the result to IP. |
1292 |
break; |
break; |
1293 |
case PPP_VJC_UNCOMP: /* VJ uncompressed TCP */ |
case PPP_VJC_UNCOMP: /* VJ uncompressed TCP */ |
1294 |
#if VJ_SUPPORT > 0 |
#if VJ_SUPPORT > 0 |
1295 |
PPPDEBUG((LOG_INFO, "pppInput[%d]: vj_un in nBuf len=%d\n", pd, nb->len)); |
PPPDEBUG((LOG_INFO, "pppInput[%d]: vj_un in pbuf len=%d\n", pd, nb->len)); |
1296 |
/* |
/* |
1297 |
* Process the TCP/IP header for VJ header compression and then pass |
* Process the TCP/IP header for VJ header compression and then pass |
1298 |
* the packet to IP. |
* the packet to IP. |
1311 |
#endif /* VJ_SUPPORT > 0 */ |
#endif /* VJ_SUPPORT > 0 */ |
1312 |
break; |
break; |
1313 |
case PPP_IP: /* Internet Protocol */ |
case PPP_IP: /* Internet Protocol */ |
1314 |
PPPDEBUG((LOG_INFO, "pppInput[%d]: ip in nBuf len=%d", pd, nb->len)); |
PPPDEBUG((LOG_INFO, "pppInput[%d]: ip in pbuf len=%d\n", pd, nb->len)); |
1315 |
pppControl[pd].netif->input(nb, pppControl[pd].netif); |
pppControl[pd].netif->input(nb, pppControl[pd].netif); |
1316 |
return; |
return; |
1317 |
default: |
default: |
1363 |
#if 0 |
#if 0 |
1364 |
PPPDEBUG((LOG_INFO, "pppDrop: %d:%.*H\n", pc->inHead->len, min(60, pc->inHead->len * 2), pc->inHead->payload)); |
PPPDEBUG((LOG_INFO, "pppDrop: %d:%.*H\n", pc->inHead->len, min(60, pc->inHead->len * 2), pc->inHead->payload)); |
1365 |
#endif |
#endif |
1366 |
PPPDEBUG((LOG_INFO, "pppDrop: nBuf len=%d\n", pc->inHead->len)); |
PPPDEBUG((LOG_INFO, "pppDrop: pbuf len=%d\n", pc->inHead->len)); |
1367 |
|
if (pc->inTail && (pc->inTail != pc->inHead)) |
1368 |
|
pbuf_free(pc->inTail); |
1369 |
pbuf_free(pc->inHead); |
pbuf_free(pc->inHead); |
1370 |
pc->inHead = NULL; |
pc->inHead = NULL; |
1371 |
pc->inTail = NULL; |
pc->inTail = NULL; |
1431 |
else { |
else { |
1432 |
|
|
1433 |
/* Trim off the checksum. */ |
/* Trim off the checksum. */ |
1434 |
if(pc->inTail->len >= 2) { |
if(pc->inTail->len >= 2) { |
1435 |
pc->inTail->len -= 2; |
pc->inTail->len -= 2; |
1436 |
pc->inLen -= 2; |
|
1437 |
|
pc->inTail->tot_len = pc->inTail->len; |
1438 |
/* Update the packet header. */ |
if (pc->inTail != pc->inHead) { |
1439 |
pc->inHead->tot_len = pc->inLen; |
pbuf_chain(pc->inHead, pc->inTail); |
1440 |
} else { |
pbuf_free(pc->inTail); |
1441 |
pc->inHead->tot_len = pc->inLen; |
} |
1442 |
pbuf_realloc(pc->inHead, pc->inLen - 2); |
} else { |
1443 |
} |
pc->inTail->tot_len = pc->inTail->len; |
1444 |
|
if (pc->inTail != pc->inHead) { |
1445 |
|
pbuf_chain(pc->inHead, pc->inTail); |
1446 |
|
pbuf_free(pc->inTail); |
1447 |
|
} |
1448 |
|
|
1449 |
|
pbuf_realloc(pc->inHead, pc->inHead->tot_len - 2); |
1450 |
|
} |
1451 |
|
|
1452 |
/* Dispatch the packet thereby consuming it. */ |
/* Dispatch the packet thereby consuming it. */ |
1453 |
if(tcpip_callback(pppInput, pc->inHead) != ERR_OK) { |
if(tcpip_callback(pppInput, pc->inHead) != ERR_OK) { |
1454 |
PPPDEBUG((LOG_ERR, |
PPPDEBUG((LOG_ERR, |
1455 |
"pppInProc[%d]: tcpip_callback() failed, dropping packet\n", pd)); |
"pppInProc[%d]: tcpip_callback() failed, dropping packet\n", pd)); |
1456 |
pbuf_free(pc->inHead); |
pbuf_free(pc->inHead); |
1457 |
#ifdef LINK_STATS |
#ifdef LINK_STATS |
1458 |
lwip_stats.link.drop++; |
lwip_stats.link.drop++; |
1459 |
#endif |
#endif |
1460 |
} |
} |
1461 |
pc->inHead = NULL; |
pc->inHead = NULL; |
1462 |
pc->inTail = NULL; |
pc->inTail = NULL; |
1463 |
} |
} |
1536 |
case PDDATA: /* Process data byte. */ |
case PDDATA: /* Process data byte. */ |
1537 |
/* Make space to receive processed data. */ |
/* Make space to receive processed data. */ |
1538 |
if (pc->inTail == NULL || pc->inTail->len == PBUF_POOL_BUFSIZE) { |
if (pc->inTail == NULL || pc->inTail->len == PBUF_POOL_BUFSIZE) { |
1539 |
|
if(pc->inTail) { |
1540 |
|
pc->inTail->tot_len = pc->inTail->len; |
1541 |
|
if (pc->inTail != pc->inHead) { |
1542 |
|
pbuf_chain(pc->inHead, pc->inTail); |
1543 |
|
pbuf_free(pc->inTail); |
1544 |
|
} |
1545 |
|
} |
1546 |
/* If we haven't started a packet, we need a packet header. */ |
/* If we haven't started a packet, we need a packet header. */ |
1547 |
nextNBuf = pbuf_alloc(PBUF_RAW, 0, PBUF_POOL); |
nextNBuf = pbuf_alloc(PBUF_RAW, 0, PBUF_POOL); |
1548 |
if (nextNBuf == NULL) { |
if (nextNBuf == NULL) { |
1549 |
/* No free buffers. Drop the input packet and let the |
/* No free buffers. Drop the input packet and let the |
1550 |
* higher layers deal with it. Continue processing |
* higher layers deal with it. Continue processing |
1551 |
* the received nBuf chain in case a new packet starts. */ |
* the received pbuf chain in case a new packet starts. */ |
1552 |
PPPDEBUG((LOG_ERR, "pppInProc[%d]: NO FREE MBUFS!\n", pd)); |
PPPDEBUG((LOG_ERR, "pppInProc[%d]: NO FREE MBUFS!\n", pd)); |
1553 |
#ifdef LINK_STATS |
#ifdef LINK_STATS |
1554 |
lwip_stats.link.memerr++; |
lwip_stats.link.memerr++; |
1556 |
pppDrop(pc); |
pppDrop(pc); |
1557 |
pc->inState = PDSTART; /* Wait for flag sequence. */ |
pc->inState = PDSTART; /* Wait for flag sequence. */ |
1558 |
break; |
break; |
|
} else { |
|
|
if (pc->inHead == NULL) { |
|
|
struct pppInputHeader *pih = nextNBuf->payload; |
|
|
|
|
|
pih->unit = pd; |
|
|
pih->proto = pc->inProtocol; |
|
|
|
|
|
nextNBuf->len += sizeof(*pih); |
|
|
|
|
|
pc->inLen = nextNBuf->len; |
|
|
pc->inHead = nextNBuf; |
|
|
} |
|
|
else { /* Since if inHead is not NULL, then neither is inTail! */ |
|
|
pc->inTail->next = nextNBuf; |
|
|
} |
|
|
pc->inTail = nextNBuf; |
|
1559 |
} |
} |
1560 |
|
if (pc->inHead == NULL) { |
1561 |
|
struct pppInputHeader *pih = nextNBuf->payload; |
1562 |
|
|
1563 |
|
pih->unit = pd; |
1564 |
|
pih->proto = pc->inProtocol; |
1565 |
|
|
1566 |
|
nextNBuf->len += sizeof(*pih); |
1567 |
|
|
1568 |
|
pc->inHead = nextNBuf; |
1569 |
|
} |
1570 |
|
pc->inTail = nextNBuf; |
1571 |
} |
} |
1572 |
/* Load character into buffer. */ |
/* Load character into buffer. */ |
1573 |
((u_char*)pc->inTail->payload)[pc->inTail->len++] = curChar; |
((u_char*)pc->inTail->payload)[pc->inTail->len++] = curChar; |
|
pc->inLen++; |
|
1574 |
break; |
break; |
1575 |
} |
} |
1576 |
|
|
1581 |
avRandomize(); |
avRandomize(); |
1582 |
} |
} |
1583 |
|
|
|
/* |
|
|
* pppMPutC - append given character to end of given nBuf. If the character |
|
|
* needs to be escaped, do so. If nBuf is full, append another. |
|
|
* Return the current nBuf. |
|
|
*/ |
|
|
static struct pbuf *pppMPutC(u_char c, ext_accm *outACCM, struct pbuf *nb) |
|
|
{ |
|
|
struct pbuf *tb = nb; |
|
|
|
|
|
/* Make sure there is room for the character and an escape code. |
|
|
* Sure we don't quite fill the buffer if the character doesn't |
|
|
* get escaped but is one character worth complicating this? */ |
|
|
/* Note: We assume no packet header. */ |
|
|
if (nb && (PBUF_POOL_BUFSIZE - nb->len) < 2) { |
|
|
tb = pbuf_alloc(PBUF_RAW, 0, PBUF_POOL); |
|
|
if (tb) { |
|
|
nb->next = tb; |
|
|
} |
|
|
#ifdef LINK_STATS |
|
|
else { |
|
|
lwip_stats.link.memerr++; |
|
|
} |
|
|
#endif /* LINK_STATS */ |
|
|
nb = tb; |
|
|
} |
|
|
if (nb) { |
|
|
if (ESCAPE_P(*outACCM, c)) { |
|
|
*((u_char*)nb->payload + nb->len++) = PPP_ESCAPE; |
|
|
*((u_char*)nb->payload + nb->len++) = c ^ PPP_TRANS; |
|
|
} |
|
|
else |
|
|
*((u_char*)nb->payload + nb->len++) = c; |
|
|
} |
|
|
|
|
|
return tb; |
|
|
} |
|
|
|
|
|
/* |
|
|
* pppMPutRaw - append given character to end of given nBuf without escaping |
|
|
* it. If nBuf is full, append another. |
|
|
* This is normally used to add the flag character to a packet. |
|
|
* Return the current nBuf. |
|
|
*/ |
|
|
static struct pbuf *pppMPutRaw(u_char c, struct pbuf *nb) |
|
|
{ |
|
|
struct pbuf *tb = nb; |
|
|
|
|
|
/* Make sure there is room for the character and an escape code. |
|
|
* Sure we don't quite fill the buffer if the character doesn't |
|
|
* get escaped but is one character worth complicating this? */ |
|
|
/* Note: We assume no packet header. */ |
|
|
if (nb && (PBUF_POOL_BUFSIZE - nb->len) < 2) { |
|
|
tb = pbuf_alloc(PBUF_RAW, 0, PBUF_POOL); |
|
|
if (tb) { |
|
|
nb->next = tb; |
|
|
} |
|
|
#ifdef LINK_STATS |
|
|
else { |
|
|
lwip_stats.link.memerr++; |
|
|
} |
|
|
#endif /* LINK_STATS */ |
|
|
nb = tb; |
|
|
} |
|
|
if (nb) { |
|
|
*((u_char*)nb->payload + nb->len++) = c; |
|
|
} |
|
|
|
|
|
return tb; |
|
|
} |
|
|
|
|
1584 |
#endif /* PPP_SUPPORT */ |
#endif /* PPP_SUPPORT */ |